シリアル通信用関数

シリアル通信用関数

ここで利用している関数は、 LBC(Little Burning Core:©宮田耕自氏)のものをOAKS-mini用に一部書き換え、 AX-12との通信用に必要なものを付け足しました。

シリアル通信用関数解説

sci.txt
**********************************************
   シリアル通信用関数関数(UART0, UART1)
**********************************************

sci.c, sci.h

--------- UART0 ------------------------------

void UART0_ini(BaudRate b);
  引数  :BaudRate b
          ボーレート(br57600のように指定)
  戻り値:なし
  解説  :UART0の初期化
          初期値は非同期、8ビット、パリティなし、スリープなし、
          送受信許可、割り込みレベル6

int UART0_read(unsigned char *c);
    引数  :unsigned char *c
            受信データ格納用
    戻り値:int
            受信状態(0:データなし, 1:データあり)
    解説  :1バイト受信

int UART0_write(unsigned char c);
    引数  :unsigned char c
            送信データ
    戻り値:int
            送信状態(0:送信失敗, 1:送信成功)
    解説  :1バイト送信
            送信レジスタが空くまでポーリングでしばらく待つ

--------- UART1 ------------------------------

void UART1_ini(BaudRate b);
  引数  :BaudRate b
          ボーレート(br57600のように指定)
  戻り値:なし
  解説  :UART0の初期化
          初期値は非同期、8ビット、パリティなし、スリープなし、
          送受信許可、割り込みレベル6

int UART1_read(unsigned char *c);
    引数  :unsigned char *c
            受信データ格納用
    戻り値:int
            受信状態(0:データなし, 1:データあり)
    解説  :1バイト受信

int UART1_write(unsigned char c);
    引数  :unsigned char c
            送信データ
    戻り値:int
            送信状態(0:送信失敗, 1:送信成功)
    解説  :1バイト送信
            送信レジスタが空くまでポーリングでしばらく待つ

--------- 汎用関数 ----------------------------

int SCI_putchar(unsigned char c, int port);
  引数  :unsigned char c
          送信データ
          int port
          送信ポート(0:UART0, 1:UART1)
  戻り値:int
          送信状態(0:送信失敗, 1:送信成功)
  解説  :1文字送信
          改行はCR+LFに変換して送信

int printStr(unsigned char *str, int port)
  引数  :unsigned char *str
          送信データ
          int port
          送信ポート(0:UART0, 1:UART1)
  戻り値:int
          送信状態(0:送信失敗, 1以上:送信文字数)
  解説  :文字列送信
          終端文字(0x00)まで送信

int SCI_Str(unsigned char *str, int port, int n)
  引数  :unsigned char *str
          送信データ
          int port
          送信ポート(0:UART0, 1:UART1)
          int n
          送信文字数
  戻り値:int
          送信状態(0:送信失敗, 1以上:送信文字数)
  解説  :指定文字数送信

int SCI_getchar(int port)
  引数  :int port
          受信ポート(0:UART0, 1:UART1)
  戻り値:int
          受信状態(-1:ポート指定エラー, 0以上:受信文字)
  解説  :1文字受信、受信するまで待つ
          CRは改行に変換

ソースコード

sci.h
#ifndef _SCI_H_
#define _SCI_H_

/**************************************************************************
*    ボーレート設定リスト : BaudRate
*    転送速度:b pbs
*     (設定値は20M/b/16-1)近い値をとるために四捨五入
**************************************************************************/
typedef enum {
  br9600  = 129,   /* 129.208 */
  br14400 =  86,   /*  85.806 */
  br19200 =  64,   /*  64.104 */
  br28800 =  42,   /*  42.403 */
  br31250 =  39,   /*  39     */
  br38400 =  32,   /*  31.552 */
  br57600 =  21,   /*  20.701 */
  br115200 = 10,   /*   9.851 */
} BaudRate;

void UART0_ini(BaudRate b);
void int_rec_uart0(void);
int UART0_read(unsigned char *c);
int UART0_write(unsigned char c);

void UART1_ini(BaudRate b);
void int_rec_uart1(void);
int UART1_read(unsigned char *c);
int UART1_write(unsigned char c);

int SCI_putchar(unsigned char c, int port);
int printStr(unsigned char *str, int port);
int SCI_getchar(int port);
int SCI_Str(unsigned char *str, int port, int n);

#endif
sci.c
/****************************************************/
/*      ファイル名:    sci.c                       */
/*      内容:          シリアル通信用関数          */
/*      日付:          2006.05.05                  */
/*      作成者:        ono                         */
/****************************************************/

/* インクルードファイル */
#include "sfr26.h"       /* OAKSmini用定義ファイル */
#include "sci.h"

#pragma INTERRUPT   int_rec_uart0
#pragma INTERRUPT   int_rec_uart1

#define SCI_RX_BUF_SIZE 16
#define SCI_RX_BUF_MASK (SCI_RX_BUF_SIZE-1)

struct tdSCI_RX{
  unsigned short stIdx;   /* データ開始位置 */
  unsigned short edIdx;   /* データ終了位置 */
  unsigned short dataNum; /* データ数 */
  unsigned char buf[SCI_RX_BUF_SIZE];  /* データ格納 */
};

volatile static struct tdSCI_RX SCI_RX0, SCI_RX1;

/**************************************************************************
*    uart0初期設定関数 : UART0_ini()
**************************************************************************/
void UART0_ini(BaudRate b)
{
  u0mr = 0x05;       /* 送受信モ−ドレジスタ 内部クロック */
                     /* 非同期、8ビット、パリティなし、*/
                     /* スリープなし */

  u0c0 = 0x10;       /* 送受信制御レジスタ0 クロックf1選択 */
  u0brg = b;         /* 転送速度レジスタ */

  s0ric = 0x06;      /* 割込みレベルの設定(レベル6) */
  u0c1 = 0x05;       /* 送受信制御レジスタ1 送受信許可 */
  ucon = 0x00;       /* 送受信制御レジスタ2 */
}

/**************************************************************************
*    受信割り込み : int_rec_uart0()
**************************************************************************/
void int_rec_uart0(void)
{
  unsigned char c;

  /* 受信バッファに空きがあれば受信 */
  if(ri_u0c1){
    c=u0rbl;
    if(SCI_RX0.dataNum != SCI_RX_BUF_SIZE){
      SCI_RX0.buf[SCI_RX0.edIdx]=c;
      SCI_RX0.edIdx=(SCI_RX0.edIdx+1) & SCI_RX_BUF_MASK;
      SCI_RX0.dataNum++;
    }
  }
}

/**************************************************************************
*    1バイト受信 : UART0_read()
**************************************************************************/
int UART0_read(unsigned char *c)
{
  /* 受信バッファにデータがあれば取り出す */
  if(SCI_RX0.dataNum != 0){
    *c=SCI_RX0.buf[SCI_RX0.stIdx];
    SCI_RX0.stIdx=(SCI_RX0.stIdx+1) & SCI_RX_BUF_MASK;
    SCI_RX0.dataNum--;
    return(1);
  }

  /* 受信バッファが空なら何もしないで終了 */
  *c=0;
  return(0);
}

/**************************************************************************
*    1バイト送信 : UART0_write()
**************************************************************************/
int UART0_write(unsigned char c)
{
  unsigned long i;
  unsigned short f;
  
  /* 送信レジスタが空くまでポーリングで待つ */
  f=0;
  for(i=0; i<0x200000; i++){
    if(ti_u0c1){
      f=1;
      break;
    }
  }

  if(f){
    u0tb=c;
    return(1);
  }
  return(0);
}

/*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++*/

/**************************************************************************
*    uart1初期設定関数 : UART1_ini()
**************************************************************************/
void UART1_ini(BaudRate b)
{
  u1mr = 0x05;       /* 送受信モ−ドレジスタ 内部クロック */
                     /* 非同期、8ビット、パリティなし、*/
                     /* スリープなし */

  u1c0 = 0x10;       /* 送受信制御レジスタ0 クロックf1選択 */
  u1brg = b;         /* 転送速度レジスタ */

  s1ric = 0x06;      /* 割込みレベルの設定(レベル6) */
  u1c1 = 0x05;       /* 送受信制御レジスタ1 送受信許可 */
  ucon = 0x00;       /* 送受信制御レジスタ2 */
}

/**************************************************************************
*    受信割り込み : int_rec_uart1()
**************************************************************************/
void int_rec_uart1(void)
{
  unsigned char int_flag, c;

  int_flag=ri_u1c1;

  /* 受信バッファに空きがあれば受信 */
  if(int_flag){
    c=u1rbl;
    if(SCI_RX1.dataNum != SCI_RX_BUF_SIZE){
      SCI_RX1.buf[SCI_RX1.edIdx]=c;
      SCI_RX1.edIdx=(SCI_RX1.edIdx+1) & SCI_RX_BUF_MASK;
      SCI_RX1.dataNum++;
    }
  }
}

/**************************************************************************
*    1バイト受信 : UART1_read()
**************************************************************************/
int UART1_read(unsigned char *c)
{
  /* 受信バッファにデータがあれば取り出す */
  if(SCI_RX1.dataNum != 0){
    *c=SCI_RX1.buf[SCI_RX1.stIdx];
    SCI_RX1.stIdx=(SCI_RX1.stIdx+1) & SCI_RX_BUF_MASK;
    SCI_RX1.dataNum--;
    return(1);
  }

  /* 受信バッファが空なら何もしないで終了 */
  *c=0;
  return(0);
}

/**************************************************************************
*    1バイト送信 : UART1_write()
**************************************************************************/
int UART1_write(unsigned char c)
{
  unsigned long i;
  unsigned short f;
  
  /* 送信レジスタが空くまでポーリングで待つ */
  f=0;
  for(i=0; i<0x200000; i++){
    if(ti_u1c1){
      f=1;
      break;
    }
  }

  if(f){
    u1tb=c;
    return(1);
  }
  return(0);
}

/*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
   汎用関数
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++*/

/**************************************************************************
*    1文字送信 : SCI_putchar()
**************************************************************************/
int SCI_putchar(unsigned char c, int port)
{
  int (* myfunc)(unsigned char);

  if(port==0){
    myfunc = UART0_write;
  }else if(port==1){
    myfunc = UART1_write;
  }else{
    return(0);
  }

  /* 改行はCR+LFに変換して送信 */
  if(c=='\n'){
    if(!(*myfunc)(0x0D)){
      return(0);
    }
    if(!(*myfunc)(0x0A)){
      return(0);
    }
  }else{  /* それ以外はそのまま送信 */
    if(!(*myfunc)(c)){
      return(0);
    }
  }
  return(1);
}

/**************************************************************************
*    文字列送信 : printStr()
**************************************************************************/
int printStr(unsigned char *str, int port)
{
  unsigned char *s;

  /* 終端文字まで1文字ずつ表示 */
  for(s=str; *s!='\0'; s++){
    if(!SCI_putchar(*s, port)){
      return(0);
    }
  }
  return(s-str);
}

/**************************************************************************
*    指定文字数送信 : SCI_Str()
**************************************************************************/
int SCI_Str(unsigned char *str, int port, int n)
{
  unsigned char *s;
  int i;

  /* 1文字ずつ表示 */
  for(s=str, i=0; i<n ; i++){
    if(!SCI_putchar(*(s+i), port)){
      return(0);
    }
  }
  return(s-str);
}

/**************************************************************************
*    1文字受信 : SCI_getchar()
**************************************************************************/
int SCI_getchar(int port)
{
  int (* myfunc)(unsigned char *);
  unsigned char c;

  if(port==0){
    myfunc = UART0_read;
  }else if(port==1){
    myfunc = UART1_read;
  }else{
    return(-1);
  }

  /* データを受信するまで待つ */
  while(!(*myfunc)(&c)){
    ;
  }

  /* 改行文字変換 */
  if(c==0x0D){
    c='\n';
  }
  return(c);
}

since 2006/06/03(Sat)

AX-12の目次へ

トップページへ

SEO [PR] 爆速!無料ブログ 無料ホームページ開設 無料ライブ放送