製造技術者のためのディジタル技術

(組み込み型制御入門)

  1. 組み込み型制御とは

    1. 組み込み型制御

       組み込み用計算機(ここではBCと略記)の低価格化高速化に伴い、計算機を部品のように利用したシステムが多くのディジタル回路に採用されるようになりました。
      組み込みシステムでは

       プログラムで制御を行います。
       入力回路はスイッチやセンサーからの信号をBCに送る
       出力回路はBCからの信号で対象を動作させる

      ことになります。制御をプログラムで置き換えることにより、より柔軟な制御が可能になります。

    2. 必要な技術

      組み込みシステムを製作するには

       計算機のプログラムと構造
       対象からの信号をBCが読み込み可能な形に調整する入力回路
       BCからの信号で制御対象を動作させるための出力回路

      に関する技術が必要になります。

       
    3. ディジタル信号

      0,1 二つの状態をもつ信号をディジタル信号と呼びます。スイッチのオンオフ、点灯と消灯のみを表示するランプ、BCの信号、などはすべてディジタル信号です。1本のディジタル信号では2種の「情報」しか表現できませんが、複数のディジタル信号を組み合わせると、複雑な情報を表現できます。たとえば、4本のディジタル信号を利用すると、0000から〜1111まで、16種の表現が可能です。数にすると 0〜15の整数、文字にすると、0〜9、A〜F の16種の記号を表現できます。



  2. BCのハードウエア

     
    1. 入出力制御の基本:ポート

       BCは通常8本単位のディジタル「入出力ポート」をもちます。

       入出力ポートに値はプログラムで値を読んだり(input)、書いたり(output)できる。
       出力端子は1が書き込まれるとH(3〜5V)レベルになり、数mA程度の電流を流すことができる。
       出力端子は0が書き込まれるとL(0V)レベルになり、数mA程度の電流を受け取ることができる。
       入力端子はHレベルになると、BCに1を送り、Lレベルになると0を送ります。


        (レジスタはポートと読み替えてください))

    2. アナログ信号とAD、DA変換

       アナログ信号は、一つの信号線で複数の状態を持ちます。光や力のセンサー(物理量を電気量に変換する素子)はアナログ信号を出します。明るさ、音量、速度、などを無段階に制御するつまみはアナログ信号を出します。
       アナログ入力信号は必要なレベルに応じて、複数信号のディジタル信号に変換します。これをAD(Analog-Digital)変換といいます。
      たとえば、16段階に設定するには4本のディジタル信号、256段階に設定するには8本、1024段階には10本、のディジタル信号が必要です。一般に n 本のディジタル信号は 2n の状態を表現できます。
       逆に、複数のディジタル信号線から、複数のレベルをもつアナログ信号に変換することをDA(Digital-Analog)変換といいます。以下は音を取り込みそれを処理して音として出力する処理の流れです。



      アナログ信号も、ポート信号と共用になっており、プログラムで切り替えて利用します。

  3. BCのソフトウエア

    1. プログラムと命令

       組込用コンピュータは固有の数十の「命令」を組み合わせたプログラムを実行します。命令は演算命令、制御命令、入出力命令、に大別されます。

       演算命令は加減算と論理演算などがあり、データメモリや入力したデータの間で演算処理をします。
       制御命令は次に実行する命令を指定する命令です。プログラムは通常0番地の命令から、1,2,3と順番に命令を実行していきます。
       しかし、制御命令を実行すると、直前に実行した演算命令の結果によって、次に実行する命令の番地を変更することができます。
       入力命令は計算機に接続された機器からディジタル信号の値を取り込みます。
       出力命令は、計算機が処理した値を機器に出力します。

      命令を並べた制御の手順を「機械語プログラム」と呼びます。機械語は命令と同義語です。

    2. レジスタとデータメモリ

       BCにはメモリが組み込まれています。メモリは番地(address)信号とデータ信号を持ち、指定した番地のデータを読み出したり、番地とデータを指定して、データを記憶することができます。
       また、BCのCPUにはレジスタと呼ばれる高速なメモリが組み込まれています。演算は、通常レジスタ間、または、レジスタとメモリの間で行われます。

    3. C言語プログラム

       命令はBCが直接実行できますが、機械語プログラムを製作するのが煩雑です。また、BCの種類が変わるとプログラムを全部作り変える必要があります。そこで、BCの命令とは無関係に一般的な書式でプログラムを作成し、これをコンパイルして機械語プログラムに変換する方式がよく利用されます。この変換プログラムをコンパイラと呼びます。

    4. 演算命令

       C言語で、以下のプログラムを作成した場合を考えます。

       int A,B;
       B = A + 10;

      このプログラムは、Cコンパイラで次のようなプログラムに変換されます。

       (変数 A,B をデータメモリの100番地と101番地に割り当てる)
       100番地の内容(変数A)を CPUのレジスタWに読み出す。
       Wに定数10を加える
       Wの値を101番地(変数B)に記憶する

      このプログラムを次のような記号で表現します。これが機械語プログラムの原型になります。

       MOV W,100
       ADDL W,10
       MOV 101,W

      MOVは値を「移動」する意味です。MOV W,100 は100番地を読みとりそれをレジスタWに記憶する意味です。ADDL W,10 は定数10をWに加える意味です。ADDLの最後のLは、「リテラル:定数」を意味します。MOV 101,W はWを101番地に記憶することを意味します。各行は「命令」で、プログラムメモリの10番地から記憶されているモノとします。



    5. 割り込み機能

       これまでの計算機のプログラム実行の方式では、計算機はあるプログラムの実行を始めると、それが終了するまで、別のプログラムの実行を始めることはできません。でも、最近のパソコンは一度に多くのプログラムを実行しているように見えます。これは、どんな「からくり」を利用しているのでしょうか?
       実は計算機には、ハードウエアの信号により特定のプログラムを呼び出す仕掛け、があります。この仕掛けを「割り込み」機能といいます。
       例えば、10m秒毎に発生する信号で、実行するプログラムを切替えるプログラムを呼び出す「割り込み」機能を設定しておきます。この機能はタイマー割り込みと呼ばれます。メモリ中にある複数のプログラムを同時に実行できるのは、このタイマー割り込みによる「プログラム切替え」が行われるからです。

    6. プログラムの書き込み
       「パソコン」では起動すると WIndows などの OS が実行を開始し、利用者の求めに応じて必要なプログラムをハードディスクから読み込み実行します。BCでは、プログラムを予めBCのプログラムメモリに書き込み、BCはそれを実行します。

  4. BCの構造

    1. PICの構造

       ここでは、BCの例として PIC(商品名) を紹介します。PICはマイクロチップ社が提供する、1チップ(1個のIC)で、プログラム実行が可能な小型プロセッサ(計算機)です。 PICの構造は下図のようになっています。
       プログラムメモリは書き換え可能なROM(電源を落しても忘れないメモリ)で、ここにプログラムを記録します。データメモリはRAMで、高速な読みだしや書き込みが可能です。
       PICはレジスタを通して、PICの外部端子(信号線)を制御します。ポート端子は最大8*3本のディジタル信号の状態を同時に読み出したり、値を出力できます。カウンタ/タイマは、プログラムで指定した周期の信号を出力したり、計数できます。これらの端子は TTL とよぶ通常のディジタルICと直接接続可能です。
       シリアル通信は、RS232C方式やI2C(SSP)方式で外部のプロセッサと情報の交換ができます。RS232Cドライバ用のICを介してシリアル端子(COM)をもつ Windows のPCとも接続可能です。アナログ変換はアナログ信号を入力とし、それをディジタル信号に変換する機能があります。I2Cは内部の近距離のデバイス間を2本の信号でシリアルに接続する方式です(これだけ機能が入って1個300円です)。



  5. LEDの点灯実験(回路設計)

    1. 目的

       ここでは、スイッチの値を読み込み、スイッチがオンなら4個のLEDで0〜15に対応する2進数を表示し、スイッチがオフならLEDを順に右から左に点灯する制御回路を制作します。

    2. ポート制御

       BCは通常8本単位のディジタル「入出力ポート」を持ちます。入出力ポートの各端子は、プログラムで入力または出力に設定できます。
       ポートの出力端子は、1が書き込まれるとHレベル(3〜5V)になり、数mA程度の電流を流すことができます。また、0が書き込まれるとLレベル(0V)になり、数mA程度の電流を受け取ることができます。


        (レジスタはポートと読み替えてください))

       ポートの入力端子はプログラムからの入力命令に対し、Hレベルを受けると1を、Lレベルを受けると0を送ります。

    3. LED接続回路

       LEDは数mAの電流を流すと発光します。図のように、電源(5V)>抵抗>LED>PICの出力端子 を接続します。出力端子がL(0V)になると、抵抗を通して電流が流れLEDが点灯します。出力端子がH(5V)になると、LEDの両端の電圧が同じになるため電流は流れなくなりLEDは消燈します。この場合、出力端子は図のようなスイッチの役割を果たします。プログラムで出力端子に0を書き込むと点灯し、1を書き込むと消燈します。



    4. スイッチ入力回路

       図のように、電源(5V)>抵抗>スイッチ>電源(0V)を接続し、抵抗とスイッチの接続点とPICの入力端子を接続します。スイッチがオフのときは、入力端子はHレベルになり、オンのときLレベルになります。抵抗の値は1kから100kΩくらいまでの範囲ならなんでも構いません。抵抗の値が低いとスイッチがオンの時電流を消費します。抵抗の値が高いと外部からのノイズがのりやすく、読み取る値が不正確になります(PIC のポートの入力抵抗は十分高いので流れる電流はμA程度です)
       プログラムでは、スイッチがオンのとき0を読み、オフのとき1を読みます。



    5. 回路図

       4個のLEDをポートBのRB0,1,2,3 に接続します。スイッチをRA0に接続します。また、PICに電源を供給するため、PIC の6ピンを電源グランド、13ピンを電源5Vに接続します。



  6. ソフト設計

    1. プログラム説明(前半)

       ここで利用するC言語の機能や関数を簡単に説明します。

      #のつく行は、コンパイラへの指示で、実行するプログラムではありません。#include <16f648a.h> は PIC 16f648a の属性が記述されたファイル16f648a.h を取り込む指示です。

      #fuses INTRC_IO,NOWDT,NOLVP,NOMCL はPIC特有の記述で、PICの利用法を指定しています。 INTRC_IO はプロセッサのクロックとして内部クロックを利用することを指定します。NOWDT,NOMCLR、はWDT、NCLRを利用しないことの指定でづが、説明は省略します。

      #use delay(CLOCK=4000000) はプロセッサのクロックの指定で、秒あたり4000000Hz(周波数単位) のクロック(これは内臓クロック)を利用することを指定します。

      int in  ; は数学の変数の宣言に相当します。inを8ビットの整数(int)として使用することを宣言しています。

      main() からプログラムの処理を開始します。最初のout=1;  は変数 out の値を1とします。
      set_tris_a(0xFF); は「関数(function:で特定の処理を行うプログラム)」 で、Aポートを入力に設定します。0xFF は設定する数値です。同様に、set_tris_b(0xF0); はポートBを出力に設定します。

    2. プログラム説明(後半)

      while(1) { ...  } は、無条件に { ... } の間を繰り返し処理する指定です。1はtrue を意味し、「常に」とか「無条件」の指定です。PIC は以後この処理を繰り返すことになります。

      繰り返しの中で、まず、
       output_b(~out); で、out の0と1を反転した値をポートBに送ります。ポートBには発光ダイオードが接続されていますから、out の2進数の値に従い発光ダイオードが点灯します。out のビットが0の場合、ビット反転するので出力端子は1になり、LEDは発光しません。out のビットが1の場合、出力端子は0になり、LEDは発光します。

      in = input_a() ; はスイッチが接続された A ポートの値を変数 in に読み込みます。

      次は、if ( 条件 ){ A } else { B } による場合わけ制御を行います。条件が成立する場合Aを、条件が成立しない場合はBを実行します。ここでは、スイッチのオン/オフによる場合わけを行います。if ( in == 0b00000001 ) ではスイッチの値が0b00000001 のとき、条件が成立します。0b は2進数を意味し、00000001 はスイッチがオフ(1)であることを意味します。スイッチがオフのとき、PICに接続された電圧は5Vになり、1となって読み込まれます。out++; は out を1だけ増すことを指示します。

      if (out == 0b00010000) out=0; は、out が01000 になったら、0に戻すことを指示します。outは1増えると、0000>0001>0010>...>01110>01111>10000 と増えていきます。10000 は 4ビット(4個のLED)で表示できる範囲を越えますので、0に戻します。

      else {  } 以下は、スイッチがオンの場合の処理を指定します。if( (out & 0b00001111) ==0 ) out=1; は out の下位4ビットがのとき、out を1にする指示です。out が 0 の場合、シフト(左送り)をしても何も見えないからです。out=out << 1 で << は左にシフトする演算で、この場合 out を1桁左にシフトする演算です。if (out & 0b00010000) out = out | 1; は、4ビットをシフトしたとき、左から溢れた1を右に戻す処理をしています。ここで、 & は ビット毎に論理演算の AND 処理をします。

      ここまでで、if ( 条件 ){ A } else { B } の処理が終わります。最後の delay_ms(500); で、500ミリ秒経過してから次の処理に進むことを指定します。この遅延処理を入れないと、人の目に見えない速度で発光ダイオードが点滅してしまいます。

    3. プログラム

       スイッチを読み、オンならシフト、オフなら2進数で計数(1を加える)します。#include はこのPIC用の定数を回録したファイルを読み込む指示です。

      #include <16f88.h>
      
      #fuses INTRC_IO,NOWDT,NOLVP,NOMCLR//内部クロック、WDT,LVPなし
      #use delay(CLOCK=4000000) //クロック4MHz
      #use fast_io(a)
      #use fast_io(b)
      
      int in;
      int out;
      
      void main(){
      
        //setup_adc_ports(NO_ANALOGS);//AD変換は利用しない
        
        set_tris_a(0xFF);//Aポートすべて入力
        set_tris_b(0xF0);//Bポート下位4bit出力
        out=1;
              
        while(1){
           output_b(~out); //~で0,1反転し、1のとき点灯する
               
          in=input_a();//スイッチを読む
          if(in & 0b00000001){//
             out++;//outを1だけ増す
             if(out == 0b00010000) out=0;//4ビットを越えたら0にする
           }
           else {//シフトする              
              if( (out & 0b00001111) ==0 ) out=1;
                 out=out <<1;
               if(out & 0b00010000) out = out | 1;//最左ビットが1なら右から1を入れる
            }                   
           delay_ms(500);      
        }
      }

  7. 製作

    1. 部品

      PICの端子
       下は、ICを上側から見た図です。PICの左下(マークがあります)が1ピンです。上の図で右端が9ピンとなり、その反対側が10ピンになります。各ピンについた英字はその機能を意味しています。ここでは予めプログラムが書き込まれたPIC(16F88)を利用します。

       

      タクチスイッチ(正確には tactile:触覚スイッチ)で、上のボタンを押すと側面から出ている二つの端子が短絡します。端子は両側から出ていますが、2回路ではなく、同時にオン/オフします。基板上でスイッチを操作する場合便利です。



      発光ダイオードは半導体でできた発光素子で、電流を流すと発光します。発光ダイオードには極性があり、長い方の腺(写真下側)をプラス側を接続します。電圧をかける方向を間違えると発光しません。発光ダイオードは数mAから数十mA の電流で発光します。



      抵抗素子は、電流の制限、電圧の分割などに利用します。下図は1/4W(ワット)で、抵抗値はカラーパターンで識別できます。



      電池ボックス:単4二本(3V)を電源とします。スイッチ付です。



    2. 回路の製作

       まず、PICの1ピンを左下にしてパッチボードに挿入します。PICの14ピンを電源5V(上の電源バー)、5ピンを電源0V(下のグラウンドバー)に接続します。
       その横にタクトスイッチを端子のある面を上下方向にして挿入します。一方の端子をポートAの0ビット端子(RA0)に接続し、他方をグランドバーに接続します。また、RA0 に接続した端子に 抵抗 330Ωの一方を接続し、他方を電源バーに接続します。
       最後に、4本の抵抗とLEDを挿入します。LEDは長い方を上にします。電源バー>抵抗>LEDの長い端子>(溝をこえて)LEDの短い端子と接続します。ジャンパー線でLEDの下側とポートBの各端子(RB0〜RB3)に接続します。



    3. 実行

       電池の電源線の赤い線を電源バーに黒い線をグランドバーに接続し、スイッチを入れます。LEDが点灯すればOKです。スイッチをオン、オフして点灯動作を確認してください。