Sim's blog

電子工作はじめてみました

鈴商液晶をV850基板から使う(3)

2007-07-09 23:01:30 | FPGA
V850付録基板とDWM付録基板の結線です。
        FPGA           V850
信号名  pin番号        pin番号
cs      P49 (CN2 A17)  P5.2  (CN3 5pin)
sck     P47 (CN2 A16)  SCKB2 (CN3 3pin)
mosi    P48 (CN2 B16)  SOB2  (CN3 2pin)
rs      P40 (CN2 A15)  P5.3  (CN3 4pin)

最初、直接つないでみたときはうまく動きませんでした。試しに100Ω抵抗をはさんでみると動くようになりました。一応、いらないかもしれないけど10kΩでpull-upしています。このあたりの話がよく分かっていません。

合成結果ですがISE9.1で117slice(117/2448 = 4%)です。BRAMは5個(5/12 = 41%)使用しています。最大動作周波数は139.587MHzでした。

梅雨になると気力も体力もなくなってきます。夏が暑くなるとしおれてしまいます。

7/10追記 clkgenとdpramの作り方を書いておきます。

clkgenはDCMです。core generatorの「New Source Wizard - Select IP」ダイアログで「FPGA Features and Design」→「Clocking」→「Spartan-3E,Spartan-3A」→「Single DCM SP v9.1i」を選びます。
Xilinx Clocking Wizardが起動したら「CLKDV」のチェックボックスにチェックをいれて、「Input CLock Frequency」を33MHzにして、「Divide By Value」(分周)を14にします。

dpramはdual port ramです。core generatorの「New Source Wizard - Select IP」ダイアログで「Memories & Storage Elements」→「RAMs & ROMs」→「Dual Port Block Memory v6.3」を選びます。
Dual Port Memoryダイアログが起動したら「Width A」を8に、「DepthA」を9216にします。次に「WidthB」のリストボックスから8を選びます(順番があります。DepthAの倍数がリストから選べます)。PortAをWrite Only、PortBをRead Onlyにします。ここでGenerateボタンを押すとdpramのできあがりです。RAMですが初期値を入れることもできます。

鈴商液晶をV850基板から使う(2)

2007-07-09 22:42:10 | FPGA
昨日の続きです。昨日はV850の制御ソフトだったので今日はFPGA側のRTLです。

メインモジュールは、4つのサブモジュールを結合しています。
- clkgenは基本クロックを分周してlcd用の2.3MHzを作っています
- spiはSPIの受信と書き込み用アドレスの発生やコマンドの処理をします
- dpramはデュアルポートメモリで9k byteのvramです。
- lcdは鈴商液晶の制御と読み込み用のアドレスを発生します。

`default_nettype none
module main (
    output [3:0] lcd_d,
    output cl1, cl2, frm, lcd_m,
//  output [4:0] ctrl,
    output led,
    input cs, rs, sck, mosi,
    input iclk);

    wire [4:0] ctrl;
    wire [13:0] adr;
    wire we;

    wire clk, lcd_clk;
    wire [13:0] lcd_adr;
    wire [7:0] ram_out, spi_out;

    assign led = 1'b0;

    // clkgenインスタンス
    clkgen cg (
        .CLKIN_IN(iclk),
        .RST_IN(1'b0),
        .CLKDV_OUT(lcd_clk),
        .CLKIN_IBUFG_OUT(),
        .CLK0_OUT(clk),
        .LOCKED_OUT());

    // SPI
    spi spi0 (
        .adr(adr),
        .out(spi_out),
        .ctrl(ctrl),
        .we(we),
        .cs(cs),
        .rs(rs),
        .sck(sck),
        .in(mosi),
        .clk(clk));

    // dpramインスタンス portA: SPI, portB:LCD
    dpram ram0 (
        .addra(adr),
        .addrb(lcd_adr),
        .clka(clk),
        .clkb(clk),
        .dina(spi_out),
        .doutb(ram_out),
        .wea(we));

    // 鈴商LCDインスタンス
    lcd lcd0 (
        .adr(lcd_adr),
        .in(ram_out),
        .d(lcd_d),
        .cl1(cl1),
        .cl2(cl2),
        .frm(frm),
        .m(lcd_m),
        .clk(lcd_clk));

endmodule


clkgenとdpramはcore generatorを使って作りました。基本的な使い方は前回と一緒ですが、作るものが違います。

SPIの受信とコマンドの実行を行うspiモジュールです(spi.v)
`default_nettype none
module spi (
    output reg [13:0] adr = 14'h0,  // ramアドレス
    output reg [7:0] out,           // ramへの書き込みデータ
    output reg  we = 1'b0,          // ramへの書き込み信号 1:書き込み
    output reg [4:0] ctrl = 5'h18,  // lcd制御 4:pwr 3:dsp 2-0:コントラスト
    input cs,                       // 1:disable 0:enable
    input rs,                       // 0:command 1:data
    input sck,                      // 立ち上がりでデータ取得
    input in,                       // 入力データ
    input clk);

    reg [1:0] ck = 2'b00;   // sck立ち上がり検知用シフトレジスタ
    reg d;                  // 入力ラッチ
    reg [2:0] ctr = 0;      // 入力bit数カウンタ
    reg s = 1'b0;           // 1:2byte目
    reg [5:0] adrh;         // adrの上位記憶用

    wire [7:0] data = {out[6:0], d};

    always @(posedge clk) begin
        ck <= {ck, sck};
        d <= in;
        if(cs) begin ctr <= 0; s <= 1'b0; end
        if(we) begin we <= 1'b0; adr <= adr == 14'h23ff ? 14'h0000 : adr + 1; end
        if(~cs & ck == 2'b01) begin // 立ち上がり発見
            out <= data;
            ctr <= ctr + 1;
            if(ctr == 7) begin
                if(rs) we <= 1'b1;
                else if(s) begin s <= 1'b0; adr <= {adrh, data}; end
                else if(data[7]) begin s <= 1'b1; adrh <= data[5:0]; end
                else if(data[6]) ctrl <= data[4:0];
            end
        end
    end

endmodule

sckの立ち上がりを見つけてシフトレジスタにためていって、8個たまったら、RAMへ書き込むかコマンドの実行をします。

鈴商LCDの制御です。前回と較べてクロックの分周を外に出したので少し簡単になっています。
`default_nettype none
module lcd (
    // ram interface
    output reg [13:0] adr = 14'h002f,
    input [7:0] in,
    // lcd interface
    output [3:0] d,
    output reg cl1 = 1'b0,
    output reg cl2 = 1'b1,
    output reg frm = 1'b1,
    output reg m   = 1'b1,
    // clock
    input clk);

    reg [6:0] x = 0;
    reg [7:0] y = 0;

    assign d = x[0] ? in[7:4] : in[3:0];

    // cl1, cl2
    always @(posedge clk) begin
        cl2 <= ~cl2;
        cl1 <= cl2 & x == 99;
    end

    // x, y, d, frame, m
    always @(posedge clk)
        if(~cl2) begin
            x <= x == 99 ? 0 : x + 1;
            if(x == 99) begin
                y <= y == 191 ? 0 : y + 1;
                if(y == 191) begin frm <= 1'b1; m <= ~m; end
                if(y == 0) frm <= 1'b0;
            end
        end

    // adr
    always @(posedge clk)
        if(~cl2)
            if(x == 99)   adr <= y == 191 ? 14'h002f : adr + 97;
            else if(x[0]) adr <= adr - 1;

endmodule


最後はucfファイルです。
NET "iclk"  LOC = "P88" ; 
NET "led"   LOC = "P98" ; 

NET "cs"    LOC = "P49" ;
NET "sck"   LOC = "P47" ;
NET "mosi"  LOC = "P48" ;
NET "rs"    LOC = "P40" ;

NET "cl1"   LOC = "P60" ; # A03
NET "cl2"   LOC = "P61" ; # B03
NET "frm"   LOC = "P62" ; # A04
NET "lcd_m" LOC = "P63" ; # B04
NET "lcd_d<3>"  LOC = "P53" ; # A01
NET "lcd_d<2>"  LOC = "P54" ; # B01
NET "lcd_d<1>"  LOC = "P57" ; # A02
NET "lcd_d<0>"  LOC = "P58" ; # B02


一応、LCDのパワー制御用のコマンドもこっそり作っていますが、まだ試していません。

なんかblogにソースを貼るのが面倒になってきました(笑)
ここはpreタグの中でも<とかが化けるので&lt;に変換してから貼らないといけません。
zipで固めてダウンロードしてみたいなのは、blogじゃ駄目なんでしょうか?
よそにダウンロード専用のホームページとか作るのかな?goo以外のblogだとできたりするんでしょうか?

だんだん手抜きっぽくなってきてますが、RTLはこんな感じです。

鈴商液晶をV850基板から使う(1)

2007-07-08 21:20:43 | V850
V850付録基板から鈴商液晶を使ってみようと思いました。ソフトだけでやると間に合わないっぽいので、DWM付録基板のFPGAを使うことにしました。FPGAへの出力はSPIにします。長くなりそうなので、V850側からはじめます

V850は3線式のシリアル通信機能をもっているので、そのまま使います(ユーザーズマニュアル16章)。コマンドを送っているのかデータを送っているのかを区別するための信号(RS)を追加します。
V850付録基板のpin配置
RS   P5.3  (CN3 5pin) 0:コマンド 1:データ
CS   P5.2  (CN3 4pin) 1:disable 0:enable
SCK  SCKB2 (CN3 3pin) SPI送信クロック (CSIB2)
MOSI SOB2  (CN3 2pin) SPI送信データ   (CSIB2)

データは横8dotを1byteにすると384x192dotは48x192byteになります。FPGA側にRAMを持たせて0000番地~23ff番地の9k byteに左上のdotから並んでいることにしました。アドレスは自動的にインクリメントされるのでデータを送ってやれば左上から順に描画されます。コマンドはアドレスを変更するのに使います。アドレスは14bitあるので、2回に分けて送ってやる必要があります。
転送先アドレス変更コマンドの概要
RS = 0
1byte目 0x80 + アドレス上位6bit
2byte目 アドレス下位8bit

appliletを使って雛形を作ります。

- システムは、ウォッチドックタイマーを使用しない、オンチップデバッグを使用する。
- ポートは、P52とP53を出力にする
- シリアルは、CSIB2を使用する
- CSIB2の設定は、受信許可なし、送信許可あり、コールバックは送信完了にして他はデフォルトのままにします。

デフォルトだとデータ長8bit、MSBから送信、1Mbps、データ位相はタイプ1になっています。データ位相は立上り/立下り、正パルス/負パルスの組み合わせで4種類あります。詳しくはユーザーズマニュアルの16章に載っています。

mainはこんな感じです
#define CS P5.2
#define RS P5.3

#define CMD  0
#define DATA 1

UCHAR vram[48*192];

// SPI送信
void send(UCHAR rsel, UCHAR *p, USHORT size)
{
    extern volatile UCHAR done;
    RS = rsel;                 // 0:コマンド 1:データ
    done = 0;
    CSIB2_SendData(p, size);   // 送信
    while(!done) ;             // 送信完了まで待つ
}

void  main( void )
{
    UCHAR cmd[2] = {0x80, 0x00};

    // ここでvramに何か描く

    CS = 0;
    send(CMD, cmd, 2);         // コマンド送信
    send(DATA, vram, sizeof(vram)); // データ送信

    while (1) ;                // 無限ループ
}

コマンドで転送先を0番地にしてから、vramの内容を一気に送っています。SPIへの送信はポーリングで完了待ちしています。

送信完了のコールバック(SERIAL_user.c)はこんな感じです。
volatile UCHAR done;

void CALL_CSIB2_Send( void )
{
    done = 1;
}

volatileな変数doneを使って完了通知をします。

CSIB2の設定で、転送モードを単発転送モードでなく連続転送モードにすることもできます。いまいち違いがよく分かっていませんが、連続にすると送信に割り込みを使うようです。V850のDMAは転送先をポートにしたり、転送のトリガーを完了割り込みにしたりできるので、DMAでSPIにデータを転送することもできるみたいです。

(脳内)マイコンレース

2007-07-04 08:30:39 | その他のマイコン
テクニカルライター後田 敏の部屋さんではマイコンレースというのをしています。
ここでは別の切り口で、内部構造からマイコンレースをしてみようと思います。名称、順番は後田さんと同じにしました。

PICマイコン


R8Cマイコン


78Kマイコン


HC08マイコン


MSPマイコン


AVRマイコン


その他のマイコン


えっと、コメントはさしひかえさせていただきます(笑)
ちなみに私のは・・・


脳内メーカーはこちらです。


ws☆NakさんのAVR USB DIPモジュール#168

2007-07-02 22:53:25 | AVR
ちっちゃいマイコンボードが大好きなんですが、workshop NakさんAVRマイコンのキットの販売が始まったことをkumanさんの掲示板で知りました。

かわいいので物欲ばりばりですが、これって他にライターとかいるのかな?とりあえず悩み中ですが、セット販売は限定みたいなのであまり悩んでもいられなさそうです。キットなので自分ではんだづけできるのかも不安です(笑)。

他にも色々とブレッドボードに挿せるようなモジュールがいっぱい売っています。ブレッドボードというあたりがピンポイントです。

サンハヤトの代理店情報

2007-07-02 21:36:08 | 電子工作
何気にサンハヤトのホームページを見ていたら代理店情報というのがありました。サンハヤト製品を扱っている所一覧なんですが、販売店ってなっている所は要はパーツ屋さんですね。日本全国のパーツ屋さんが分かるので便利。

北海道旭川市にはアジア電子とクラフト電子があるのが分かります。ググってもどちらもHPはないようです。そういえば昔あった御幸電子はもうなくなったのかな。探してみるとFreeLabというパーツの通販ショップが旭川にあるようです。旭川は昔住んでいた所なんで調べてみました。

検索してたら全国のパーツ屋リストみたいなページがありました(ここ)。

コンフィグレーション回路を作ってみました(続き)

2007-07-01 18:33:13 | FPGA
昨日ブレッドボードで作ったコンフィグレーション回路をユニバーサル基板で作ってみました。

左下のピンヘッダをDWM付録FPGA基板のCN3に直接させるようになっています。

手元に、DIP25pin <--> MIL26pin変換ケーブルがあったのでMIL26pinのL字コネクターをつけています。普通のDIP25pin用のコネクタはたがいちがいになっていて、ユニバーサル基板にそのままつけれませんが、向きを横にして基板をはさむようにすればつけれます。

変換基板をはずしてみたところです。

コンデンサーは変換基板の下につけています。

裏側です(笑)


一応、回路図です。

ほとんどデザインウェーブそのままですが、2.5Vから電源を取るようにしたところと、パスコンをいれたところが違っています。

部品です。
TC74LCX244 1個 (マルツ168円)
100Ω抵抗 8個
100pFコンデンサー 4個 (101)
0.1uFコンデンサー 1個 (104)
26pinコネクター(ヒロセ製 日米商事で30円くらい)
変換基板 ダイセンDO20 (マルツで5枚セット550円)
丸ピンICソケット・両端オスピン(シングル20P) (秋月のP-269 100円)
丸ピンICソケット(シングル20P) (秋月のP-241 70円)
ユニバーサル基板
ピンヘッダ 2x4 (1x4を2つ並べました)
線材少々

変換基板は丸ピンしかささらないです。20pinのを2つに割って使いました。