So-net無料ブログ作成
English Version

CNCルータでの両面基板制作 HeightMap [CNC]

 「レトロマイコンZ80ボードの構想(その18)BDS-C」の記事に貼った写真のように3チップ構成のCP/Mボードの両面基板の作成が難航しています・・^^;

 10cm程度の大きさの基板では基板の歪み?等からZ軸を一定にすることが難しくなってきてミリング不足で銅層を切断できない部分が発生してしまいます。

 使用しているgrblControl Ver0.8にはHeightMapを自動生成する機能があり、「マーティーの工房日誌」等を参考にさせて頂きHeightMap機能を使ってみました。

 コントロール基板のA5端子がエンドミルと基板の導通状態の入力になり、エンドミル部分とモーターのケースが導通状態だったので、モーターケースにピンヘッダを半田付けし、コントロール基板のGNDを接続しています。ネット情報ではモーターシャフトに接続している例が殆どですが、モーターケースに取付けることで取り外し忘れによるシャフトへのコードの絡まり事故の危険がなくなります。

 また、モータ側をA5にしている例が殆どですがモーターからのノイズを考慮してGND側を接続しました。


ハイトマップ用ピン


 A5端子からケーブルを伸ばしてミノムシグリップで基板に接続した状態でプローブしてMAPを自動生成しました。
 基板の浮きによる測定誤差が出ないように基板は捨て板(MDF)に両面テープで張り付けました。
 (両面テープはScoch製の「はがせる両面テープ」(厚さ0.15mm)を使っていて剥がし易いように基板側の接着面を手で何回かタッチして粘着力を低下させてから貼り付けましたが結局剥がすのが大変でした・・これは今後の課題です)

自動生成されたハイトマップ


 赤い部分が上に上がっている(Z軸の数値が大きい)部分です。
 Z軸のゼロ調整の同じ原理で自動でできるのですが、従来の手作業でやっていた時より結構上側で調整されました。
 手で調整する時はエンドミルを少し基板に押し付ける感じでやっていてパターン切削時のZ軸は-0.04~-0.06mm程度の設定にしていましたが、今回はZ軸-0.06mmではミリングが不十分で結局-0.12mmの位置をゼロに設定し直しました。

 しかし、ミリング結果は(写真を撮ってない^^;)は上図の赤色部分(特に奥の方)が切削不足という結果でした orz
 原因はマイクロレベルで右側が浮いていた?(であれば捨て板への基板の取付方法が問題ということになる)

 結局、HeightMapを未使用状態にして、切削不足の部分を再度切削し直しました。
 (NCVCでNCファイルを再生させて必要な部分を特定してからテキストエディタでNCファイルを編集して必要な部分のみ残す・・という作業をしています^^;)

 トップ面は明日やってみます・・・

ボトム面切削結果



★2018/04/29 追記

 トップ面のミリングをやってみました。
 CNCでアウトラインの切出しも行ったのでボトム面も含め写真を貼っておきます。

ボトム面



トップ面



 ボトム面とトップ面の位置合せは四隅に開けた穴で行っていてソルダーレジスト塗布時にPCBに穴があると穴にソルダーレジストが詰まるので次の順番での作業を予定しています。
  1. ボトム面の切削
  2. 四隅の穴開け
  3. トップ面の切削
  4. 基板切り出し
  5. ソルダーレジスト塗布
  6. 残りの穴開け

 トップ面の切削開始時に最初に左下のホールのアイソレーション用の円形を切削するのですが、ホールの位置にたいしてズレていることが判りました。
 そこで原点のY軸側を+0.8mmして穴が中心になるように調整しました(それまで原点はいじっていないのに何故ずれた??)

 トップ面の切削結果を見ると右側の二つのホールをアイソレーションする円形の切削がY軸に+0.8mm程度ズレてしまっていますねぇorz

 最初は切削の深さが足りなかったので調整したのですが、Y軸調整する前の切削痕が残っていました。(マイクロスコープは上下左右が逆転します)

ボトムとトップのY軸ズレ(トップ面左下ホール部)


 現象としてはX軸が約100mm進むとY軸が0.8mm増加するということになります。
 これはCNCのX軸とY軸が正確に直行していないということだと思います。この調整は結構大変そう・・・

 久々にマイクロスコープを使ったのでボトム面のViaとトップ面のTQFPのピンを貼っておきます。

 ボトム面は今回ほぼ想定通りの切削が出来ました。

ボトム面のVia



 トップ面は直線部分が少しヨレヨレになっているところもあり、想定より悪い状態です。
 特にTQFP周りは配線がかなり細くなったり、TQFPのピン間に余分な細い銅層が残ったりしていて想定より悪い出来でした。
 ボトム面の切削時は両面テープで基板を固定していたのですが剥がすのが結構大変だったのでトップ面では基板の淵をマスキングテープで固定して切削しました。
 流石にマスキングテープでは固定力が弱かったことが出来の悪さの一つの原因ではないかと思います。

トップ面のTQFPのピン



★2018/04/30 追記
 切削した基板を眺めてみると腑に落ちない点が出来てきました。

 DesignSparkMechanicalを使って再現シミュレーションをしてみました。
 始めに歪みがある状態でボトム面を再現

ボトム面再現


 次の手順(1項は上記の操作)で検証してみました。
  1. (x、y)=(100,70)の四角形の右端の辺を0.5mm上(Y軸)にずらした平行四辺形を作成
  2. 厚さ1mm(Z軸)の3Dオブジェクト化(紫色)
  3. Z軸方向に2mm移動して複写(ピンク色)
  4. 複写したものをY軸で180度回転
  5. 左下のホールがズレるので複写したものを-0.5mmY軸方向に移動


 再現結果が下図です。

トップ面(ピンク)再現
 

 確かに今回起きた現象が再現されます。

 ここで不思議なのが基板切り出しはトップ面で行っているのでボトム面の基板の淵の四角形が切出した基板に対して傾いているはずなのですが上のボトム面の写真を見ると基板の切出しと基板の淵の四角形の関係は傾いておらず、Y軸のみ0.8mmズレているように見えます・・・・何故??

 ボトム面の切削時に四隅に開けた位置決め用のホール(捨て板にも開いている)にトップ面を上にしてピンを立ててみました。
 ピンが多少傾きますがきちんと立ちます(なので平行四辺形ではないということ)。

 じゃ~ズレの原因はY軸の脱調??

トップ面での位置決めピン
 


[TOP] [ 前へ ] 連載記事 [ 次へ ]
nice!(1)  コメント(1) 
共通テーマ:趣味・カルチャー

ヒートガン購入 [日記]

 今まで使っていたホットガンはamazonで購入した1800Wのもので温度調整が出来ませんでした。
 ebayで温度調整機能付きで風量調整もできるものを見つけたので購入してみました。

 送風の温度を1℃単位で設定できるし送風量も調節できます。音も割合静かです。消費電力は650Wで先端に付けるアタッチメントが3種類と簡易スタンドが付属しています。
 お値段は約4400円程で従来の物の2倍くらいです。

 今まで使っていたものは今後収縮チューブ等の加工に使いますが、表面実装部品の作業は今回購入したヒートガン(従来の物はホットガンですが今回購入したものはHeatGunですw)がメインになる予定です。

 温度調整機能がない従来のものはかなり高温の熱風が出ていたようで、基板を熱しすぎるとワザワザ手作業で塗布したソルダーレジストが変質することがありました。

 今回購入したものは温度設定ができるのでebayで購入したソルダーペースト(ケースに低溶点と書いてある)で試したところ220°付近で溶けだしたので230°の設定で使えば良さそうです。この温度ではソルダーレジストは変質しないことも確かめました。

★2018/04/26 追記 {
 使用したソルダーペーストのケースには sn45pb35bi20と成分比が書いてありました(Sn:錫、Pb:鉛、Biは・・ビスマス)。融点は220℃より低いものと思います。手持ちでもう1種類あるソルダーペーストは「Sn63/Pb37 183℃」と書かれていてネットで調べると錫と鉛の混合ではこの比率の時が融点が最も低くなるようです。
}

 ネット情報ではホットプレートやトースターなどを改造してリフローしている人が多いようですが、私は両面に部品を実装したいのでヒートガン派です(お手軽ですしね)
 ※下の写真では先端が黒ずんでいるように見えますが実物はピッカピカです。


HeatGun

nice!(0)  コメント(0) 
共通テーマ:趣味・カルチャー

レトロマイコンZ80ボードの構想(その18)BDS-C [Z80]

 CP/Mが動いたのでBD Software社のサイトからパブリックドメインで提供されているBDS-Cで遊んでみました。
 プロトタイプ宣言が使えなかったり引数の型宣言が昔風ですが、十分遊べるレベルです。

 ソースは「PIC24FJ64GAでGAME言語(その4)」の記事に書いたpicle言語のライフゲームソースからBDS-C用にコンバージョンしたので変数名等picle風ですw

 コンパイル時の状況は下記のとおりで、さすがにコンパイル速度は結構早い(約3秒程度)です。

BDS-Cでライフゲームのソースをコンパイル
b>dir B: BDSCPAT LBR : C CCC : C SUB : CC COM B: CC2 COM : CCONFIG COM : CHARIO C : CLIB COM B: CLINK COM : CRCK COM : CRCK DOC : CRCKLST1 CRC B: DEFF CRL : DEFF2 CRL : EXAMPLES LBR : FILES DOC B: -LBR NOT : LBREXT COM : LDIR COM : -READ ME B: SOURCES LBR : UNCRUNCH COM : ZCASM LBR : CCONFIG C B: CCONFIG H : STDIO H : CCONFIG CRL : L2 COM B: CHARIO CRL : DEFF3 CRL b>dir c: C: HELLO C : HELLO CRL : HELLO COM : LIFE C C: L2 C : L2 CRL : L2 COM : HELLO BAK C: FIBO BAK : FIBO CRL : FIBO COM : FIBO C C: LIFE CRL : LIFE COM : TBCPM COM : Z TXT C: LIFE SYM b>cc c:life BD Software C Compiler v1.60 (part I) 37K elbowroom BD Software C Compiler v1.60 (part II) 34K to spare b>clink c:life BD Software C Linker v1.60 Last code address: 131E Externals start at 131F, occupy 0C88 bytes, last byte at 1FA6 Top of memory: EC05 Stack space: CC5F Writing output... 46K link space remaining b>c:life


 実行中の様子が下のキャプチャです。同じパターンの繰り返しになると自動的に乱数でパターン生成するようにしています。

LifeGame with BDS-C on CP/M80


 ソースは次のとおりです。上記のようにpicleソースからコンバージョンしたので変数などがpicle風のままです ^^;

ライフゲーム(BDS-C on CP/M)
/* * Life Game written with BDS-C for CP/M80 * by skyriver 2018/04/15 */ #define X_SIZE 50 #define Y_SIZE 16 #define AR_SIZE ( X_SIZE * Y_SIZE ) int _Cnt[AR_SIZE]; int _Life[AR_SIZE]; int X,Y; int Gen,MaxGen; Clear() { int i; Gen = 0; for ( i = X_SIZE*Y_SIZE-1; i >= 0; i-- ) { _Cnt[i] = 0; _Life[i] = 0; } for ( i = X_SIZE*Y_SIZE/16; i > 0; i-- ) { X = rand() % (X_SIZE/2) + X_SIZE/4; Y = rand() % (Y_SIZE/2) + Y_SIZE/4; _Life[Y*X_SIZE+X] = 1; } putchar(0x1B); /* clear console */ printf("[2J"); } Init() { Clear(); srand( 123 ); } Inc() { int xx,yy,tx,ty; for( yy = Y - 1; yy <= Y+1; yy++ ) { ty = yy; if( ty < 0 ) { ty += Y_SIZE; } else if( ty >= Y_SIZE ) { ty -= Y_SIZE; } for( xx = X - 1; xx <= X+1; xx += 1 + (yy == Y) ) { tx = xx; if( tx < 0 ) { tx += X_SIZE; } else if( tx >= X_SIZE ) { tx -= X_SIZE; } _Cnt[ty*X_SIZE + tx]++; } } } main() { int mark,count,pos; int flg,flgb,scnt; Init(); scnt = 0; do { Gen = Gen+1; if ( Gen > MaxGen ) { MaxGen = Gen; } putchar(0x1B); /* move cursor to home */ printf("[0;0H"); printf("%5d", Gen); printf(" generation (Max:%5d)\n", MaxGen); flg = 0; for ( Y=0; Y<Y_SIZE; Y++ ) { for ( X=0; X<X_SIZE; X++ ) { if (_Life[Y*X_SIZE+X] == 0 ) { mark = '.'; } else { mark = 'O'; Inc(); flg++; } putchar(mark); } putchar('\n'); } for ( pos=Y_SIZE*X_SIZE-1; pos>=0; pos-- ) { count = _Cnt[pos]; _Cnt[pos] = 0; if (count == 3) { _Life[pos]=1; } else { if (count != 2) { _Life[pos]=0; } } } if ( (scnt>5) || (flg == 0) ) { Clear(); scnt = 0; flg = -1; } else { if (flg == flgb ) { scnt++; } else { flgb = flg; scnt = 0; } } } while (1); }



 話は変わりますが、CNCでのPCB化に苦戦しています。
 10cm程度の大きさになると基板面の平面に歪みが出て、部分的にミリング不足で銅層が繋がってしまう現象が発生してしまいます。
 使用している grblControl にはHeightMapを自動的に測定する機能もあるのでこれを利用できるようにしないとある程度のサイズの基板の作成作業が安定しない・・

 現状のミリング結果を貼っておきます。基板切り出し前のもので手で大きめにカットした状態のものです。

 トップ面では左上と右端が切削しきれていません・・orz

トップパターン



 ボトム面は左端が若干、銅層が切断できていない状態です。

ボトムパターン


★2018/04/21 追記
 このサイトにBDS Cについて色々な情報が書いてあり、HTML5で動くMSXエミュレータのWebMSXが紹介されていました。
 上記のLifeGameをMSX用の画面制御に変更してブラウザ表示で動かしてみましたのでキャプチャを貼っておきます。

LifeGame On MSX Webemulator


[TOP] [ 前へ ] 連載記事 [ 次へ ]
nice!(0)  コメント(3) 
共通テーマ:趣味・カルチャー

レトロマイコンZ80ボードの構想(その17)HALT以外の方法 [Z80]

 「レトロマイコンZ80ボードの構想(その12)CP/M80 BIOS検討4」の記事に書いたようにPICとZ80のインターフェースとしてHALTを使用しています。
 HALT脱出のためにRESETを使っていますがこの場合、割込み用FFと割り込みモードがクリアされるのでZ80側で割込み処理を使いたい場合には今回のHALT+RESET方式は使えません。

 簡単な回路でZ80側で割込みも使用できる方法を思いついたので実験してみました。

 PICとZ80のインターフェースにIORQ/とWAIT/を使う方法です。まずはZ80のIO Input/Outputサイクルのタイミングが下図です。


Z80 Input or Output Cycles


 TWの立下りでWAIT/がサンプリングされます。
 そこで、IORQ/を抵抗を介してWAIT/に接続し、PIC側ではWAIT/の状態を監視します(下図の接続、PA1は1例であり他のポートでも可)。
 PIC側はWAIT/がlowになったら、BUSREQ/をアクティブにしてからWAIT/を監視していたポートを出力に切替でhighを出力しZ80のWAIT状態を解除します。
 Z80側はWAIT/が解除されるのでT3サイクルの立上りでBUSREQ/を検出してBUSACK/をアクティブにしてバスを開放します。



 Z80側は単純にI/O命令(InputでもOutputでも可、Outputの場合はデータバスにPIC側に渡したい情報を載せることも可能)を実行するだけです。
 処理手順は次のようになります(下記のサンプルソースでは「PIC_SRV」部分)
  1. ワークエリアにサービスIDとサービス処理に必要なパラメータを設定
  2. I/O命令を実行
  3. PICがワークエリアに設定した処理結果を参照


 PIC側の処理手順は次のようになります(下記のサンプルソースでは「 PicSrv()」部分)
  1. WAIT/がアクティブになるまで待つ(入力ポートでWAIT/信号を監視)
  2. BUSREQ/をアクティブにする
  3. 上記のWAIT/監視ポートを出力に切替えhighを出力後、ポートを入力状態に戻す
  4. サービスIDとパラメータに従い処理し、結果をワークエリアに保存する
  5. BUSREQ/をインアクティブにする


 「レトロマイコンZ80ボードの構想(その12)CP/M80 BIOS検討4」の記事に書いたHALT+RESETを使った場合に比べてZ80/PIC双方の処理が簡単になります。(但し、WAIT/制御用のポートが余分に必要になるので今回はHALT/RESET方式を採用しています)

 上記の記事と同様にCP/MのBIOSでのコンソール入出力関連の機能で実験してみました。
 Z80のキーセンス処理のループ部分を抜き取ったロジアナ画面も貼っておきます。


Z80からPICへのサービス要求処理時の信号サンプル(WAIT方式)


 Z80側の実験用ソースは次のとおりです。
 「Start」と表示後、キー入力状態をチェックし、キー入力があった場合には入力データを読込み16進で表示します。

PIC-Z80間I/FにWAITを使用した実験(Z80:アセンブラ)
; PicSrvWa.mac : PIC service call test using IOREQ and WAIT for CP/M BIOS ; Ver 0.01 2018/04/7 by skyriver 000D CR EQU 13 000A LF EQU 10 FF00 PICSRV EQU 0FF00H ; DMA for PIC FFF0 PICWRK EQU 0FFF0H ; PIC service work area 0080 SECSIZE EQU 128 ; sector size 0000 FC_EXIT EQU 0 ; EXIT CP/M 0001 FC_CONST EQU 1 ; CONST 0002 FC_CONIN EQU 2 ; CONIN 0003 FC_CONOUT EQU 3 ; CONOUT 0004 FC_READ EQU 4 ; READ SD Card 0005 FC_WRITE EQU 5 ; WRITE SD Card 0006 FC_PIC EQU 6 ; PIC control ; ++++ work area for PIC Interface FFF0 FuncNo equ PICWRK ; ds 1 : function No FFF1 RetVal equ PICWRK + 1 ; ds 1 : return value FFF2 FCData equ PICWRK + 2 ; ds 1 : conout data FFF3 SelDk equ PICWRK + 3 ; ds 1 FFF4 Track equ PICWRK + 4 ; ds 2 FFF6 DmaAdr equ PICWRK + 6 ; ds 2 FFF8 Sector equ PICWRK + 8 ; ds 1 0000' ASEG ORG 0100H .PHASE PICSRV .Z80 FF00 31 0100 TEST: LD SP,0100h FF03 21 FF27 LD HL,MSG FF06 CD FF1D CALL PRNMSG FF09 CD FF50 LOOP: CALL CONST FF0C B7 OR A FF0D 28 FA JR Z,LOOP FF0F 21 FF31 LD HL,MSGP FF12 CD FF1D CALL PRNMSG FF15 CD FF54 CALL CONIN FF18 CD FF3A CALL PRNHEX FF1B 18 EC JR LOOP FF1D 7E PRNMSG: LD A,(HL) FF1E B7 OR A FF1F C8 RET Z FF20 4F LD C,A FF21 CD FF58 CALL CONOUT FF24 23 INC HL FF25 18 F6 JR PRNMSG FF27 0D 0A 53 74 MSG: DB CR,LF,'Start',CR,LF,0 FF2B 61 72 74 0D FF2F 0A 00 FF31 20 50 75 73 MSGP: DB ' Pushed:',0 FF35 68 65 64 3A FF39 00 FF3A PRNHEX: FF3A 47 LD B,A FF3B 1F RRA FF3C 1F RRA FF3D 1F RRA FF3E 1F RRA FF3F CD FF43 CALL PRNHNIB FF42 78 LD A,B FF43 PRNHNIB: FF43 E6 0F AND 00FH FF45 C6 30 ADD A,'0' FF47 FE 3A CP '9'+1 FF49 38 02 JR C,PRNHNIB2 FF4B C6 07 ADD A,'A' - '0' - 10 FF4D PRNHNIB2: FF4D 4F LD C,A FF4E 18 08 JR CONOUT ; ; check console key data ; A -> 0ffh:data exist 00h:none FF50 CONST: FF50 3E 01 LD A,FC_CONST FF52 18 0C JR PIC_SRV ; ; input console ; A -> key data FF54 CONIN: FF54 3E 02 LD A,FC_CONIN FF56 18 08 JR PIC_SRV ; ; out console ; C <- data FF58 CONOUT: FF58 79 LD A,C FF59 32 FFF2 LD (FCData),A FF5C 3E 03 LD A,FC_CONOUT FF5E 18 00 JR PIC_SRV ; ; PIC Service Function ; A <- service no ; A -> return value FF60 PIC_SRV: FF60 32 FFF0 LD (FuncNo),A FF63 D3 55 OUT (55H),A ; wait with IORQ and release by PIC FF65 3A FFF1 LD A,(RetVal) FF68 C9 RET END


 PIC側では上記のZ80のアセンブル結果のバイナリファイルを MemWr() での書込み処理に変換するツールを作り、picleソース内に取り込んでいます。
 PIC側でのリスト表示と実行結果を下記に示します。
 末尾にある「pushed」の部分は '1'、'2'、'3'のキー入力をした結果です。

PIC-Z80間I/FにWAITを使用した実験(PIC側:picle言語)
:l 1:# Test IORQ & WAIT I/F to Z80 by skyriver 2018/04/07 2: 3:use LibCpm; 4: 5:var ProgStart,ProgWrk,_WrkVal; 6: 7: 8:proc InitProg() { 9: ProgStart = $ff00; # Prog start addr 10: ProgWrk = $fff0; # Prog work addr 11: _WrkVal = Alloc( 5 ); 12: 13: PmpOn(); 14: 15: PmpSetAdr( 0 ); 16: MemWr( $c3 ); 17: MemWr( $00 ); 18: MemWr( $ff ); 19: 20: PmpSetAdr( ProgStart ); 21: 22: MemWr( $31 ); MemWr( $00 ); MemWr( $01 ); MemWr( $21 ); MemWr( $27 ); 23: MemWr( $ff ); MemWr( $cd ); MemWr( $1d ); MemWr( $ff ); MemWr( $cd ); 24: MemWr( $50 ); MemWr( $ff ); MemWr( $b7 ); MemWr( $28 ); MemWr( $fa ); 25: MemWr( $21 ); MemWr( $31 ); MemWr( $ff ); MemWr( $cd ); MemWr( $1d ); 26: MemWr( $ff ); MemWr( $cd ); MemWr( $54 ); MemWr( $ff ); MemWr( $cd ); 27: MemWr( $3a ); MemWr( $ff ); MemWr( $18 ); MemWr( $ec ); MemWr( $7e ); 28: MemWr( $b7 ); MemWr( $c8 ); MemWr( $4f ); MemWr( $cd ); MemWr( $58 ); 29: MemWr( $ff ); MemWr( $23 ); MemWr( $18 ); MemWr( $f6 ); MemWr( $0d ); 30: MemWr( $0a ); MemWr( $53 ); MemWr( $74 ); MemWr( $61 ); MemWr( $72 ); 31: MemWr( $74 ); MemWr( $0d ); MemWr( $0a ); MemWr( $00 ); MemWr( $20 ); 32: MemWr( $50 ); MemWr( $75 ); MemWr( $73 ); MemWr( $68 ); MemWr( $65 ); 33: MemWr( $64 ); MemWr( $3a ); MemWr( $00 ); MemWr( $47 ); MemWr( $1f ); 34: MemWr( $1f ); MemWr( $1f ); MemWr( $1f ); MemWr( $cd ); MemWr( $43 ); 35: MemWr( $ff ); MemWr( $78 ); MemWr( $e6 ); MemWr( $0f ); MemWr( $c6 ); 36: MemWr( $30 ); MemWr( $fe ); MemWr( $3a ); MemWr( $38 ); MemWr( $02 ); 37: MemWr( $c6 ); MemWr( $07 ); MemWr( $4f ); MemWr( $18 ); MemWr( $08 ); 38: MemWr( $3e ); MemWr( $01 ); MemWr( $18 ); MemWr( $0c ); MemWr( $3e ); 39: MemWr( $02 ); MemWr( $18 ); MemWr( $08 ); MemWr( $79 ); MemWr( $32 ); 40: MemWr( $f2 ); MemWr( $ff ); MemWr( $3e ); MemWr( $03 ); MemWr( $18 ); 41: MemWr( $00 ); MemWr( $32 ); MemWr( $f0 ); MemWr( $ff ); MemWr( $d3 ); 42: MemWr( $55 ); MemWr( $3a ); MemWr( $f1 ); MemWr( $ff ); MemWr( $c9 ); 43: 44:} 45: 46: 47:proc PicSrv() { 48: var i,fno,rval; 49: 50: while (1) { 51: while ( LATA[-1] & 2 ) {} # wait IORQ 52: PmpOn(); # BUSREQ 53: LATA[-2] = LATA[-2] & $fffd; # set port output to set wait to high 54: LATA[-2] = LATA[-2] | 2; # set port input 55: 56: PmpSetAdr( ProgWrk ); 57: 58: fno = MemRd(); # dummy 59: for ( i=0; i<9; i=i+1 ) { 60: _WrkVal[i] = MemRd(); 61: } 62: fno = _WrkVal[0]; # function No 63: if ( fno = 1 ) { # CONST 64: if ( InpChk_() ) { 65: rval = $ff; 66: } else { 67: rval = 0; 68: } 69: } 70: else if ( fno = 2 ) { # CONIN 71: rval = InpChar_(); 72: } 73: else if ( fno = 3 ) { # CONOUT 74: PrnChar_( _WrkVal[2] ); 75: rval = 0; 76: } else { 77: PrnStr_( "\nFunc err" ); 78: } 79: PmpSetAdr( ProgWrk + 1 ); 80: MemWr( rval ); 81: PmpOff(); 82: BusRelease(); 83: } 84:} 85: 86: 87:proc main() { 88: init(); 89: initPmp(); 90: InitProg(); 91: 92: LATA[0] = LATA[0] | 2; # set WAIT release 93: 94: dump( 0 ); 95: dump( ProgStart ); # dump & PmpOff 96: LATC[0] = $0000; # reset on 97: BusRelease(); 98: LATC[0] = $0001; # reset off 99: 100: PicSrv(); 101:} :run 0000 : C3 00 FF 00 00 C3 06 EC FE 43 FE 43 FE 43 FE 43 0010 : FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 0020 : FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 0030 : FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 0040 : FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 0050 : FE 43 FE 43 FE 43 FE 43 FE 43 FE 43 00 20 20 20 0060 : 20 20 20 20 20 20 20 20 00 00 00 01 00 20 20 20 0070 : 20 20 20 20 20 20 20 20 00 00 00 00 00 FB EE FA FF00 : 31 00 01 21 27 FF CD 1D FF CD 50 FF B7 28 FA 21 FF10 : 31 FF CD 1D FF CD 54 FF CD 3A FF 18 EC 7E B7 C8 FF20 : 4F CD 58 FF 23 18 F6 0D 0A 53 74 61 72 74 0D 0A FF30 : 00 20 50 75 73 68 65 64 3A 00 47 1F 1F 1F 1F CD FF40 : 43 FF 78 E6 0F C6 30 FE 3A 38 02 C6 07 4F 18 08 FF50 : 3E 01 18 0C 3E 02 18 08 79 32 F2 FF 3E 03 18 00 FF60 : 32 F0 FF D3 55 3A F1 FF C9 E5 E5 E5 E5 E5 E5 E5 FF70 : 00 00 0A 00 54 00 80 00 00 E5 E5 E5 E5 E5 E5 E5 Start Pushed:31 Pushed:32 Pushed:33



[TOP] [ 前へ ] 連載記事 [ 次へ ]

nice!(0)  コメント(3) 
共通テーマ:趣味・カルチャー

レトロマイコンZ80ボードの構想(その16)回路図とPCB化 [Z80]

 前回の記事でWordStarも動いたことを追記しましたが、CP/Mは動いているようなので回路図を整理し、パターン設計してみました。

 回路図は下記のとおりで、PIC24FJ64GA004の少ないI/Oで対応していて主な特徴は次のとおりです。
 尚、CADソフトはDesignSparkPCBを使っています。
  • 実装IC
     当初の目標どおり、3チップ構成でTTL等は使用していません。
    • Z84C0020PEC(Z80 20MHz:40-Pin DIP) 16MHzで動作
    • HM628128ALP-7(128Kbytes SRAM アクセスタイム 70ns:32-Pin DIP)
    • PIC24FJ64GA004(44-Pin TQFP) 32MHzで動作
  • 外部メモリのアクセス範囲
     PICから64KB全空間をアクセスできた方がいいですが、CP/Mを立ち上げるための必須条件はメモリ領域の最初と最後の領域だけアクセスできればいいのでPICからのメモリアクセス範囲は
    • 0000h - 07FFh
    • F800h - FFFFh
    の範囲にしています。
  • Z80-PIC 間インターフェース
     HALTを使用していますが、I/O数削減のため、HALT脱出のためにNMI(INT)ではなくRESETを使っています。詳細はここを参照してください。
  • Z80のクロック
     PICに内蔵している発信器のクロックをZ80へ供給している(Z80は16MHzで動作)ので外付けのクリスタルも不要です。
  • スイッチ入力用ポートでLED制御用のポートを兼用しています。


Pic24CPMの回路図 Ver0.01



 次にパターン図ですが、TQFT変換基板の作成記事の時のようにCNCでプリント基板を作る予定なので、私のCNC環境で制作できそうな範囲内で小型化してみました(基板サイズは100mm x 70mm)。

 回路的にはシンプルなので割合簡単にできると思っていたら結構、時間が掛かりました。
 SDカードのフットプリントはDesignSparkさんのサイトで探しましたが、手持ちのSDカードホルダと同じものが無かったので自作しています。

 最初は別のICの配置でパターン設計を進めていましたが、PIC24FJの部分で行き詰りそうだったので途中でICの配置を変更しています(最初の配置パターンはtwitterを参照してくださいw)。
 斜めのコネクトラインが何本か残っていますが、これらはグランドの接続で、グランドをベタパターン化することで接続されるので問題ありません。

★2018/04/02 追記 {
 CNCで制作するために考慮した点は次のとおりです。
  • ピンヘッダ
     ピンヘッダ部分はスルホール処理をしないのでボトム面で結線する(ICソケットは丸ピンタイプのものを使用してトップとボトムの両面を半田付けするので対象外)
  • PowerトラックのVia
     Viaはスズメッキ線を通して処理(曲げ固定Via処理法)するのでVia部の抵抗は小さいため、Powerトラック用Viaも通常のサイズのものを使用している。
  • Via
     Via処理も手作業になるのでなるべくビア数は少なくした(つもり)。
  • TQFP取付部
     Via処理後はViaが基板面から出っ張るのでTQFPの半田付け作業の邪魔にならないようにTQFPの直下にはViaを打たない。
}

パターン図(GNDベタ化前)


 グランドをベタパターン化後のトップ面とボトム面のパターンが下の2つの図です。
 基本としてはトップ面を横方向、ボトム面を縦方向の接続パターンにしていますが、PIC周りでは臨機応変に接続しています。

トップ面のパターン(GNDベタ化後)

ボトム面のパターン(GNDベタ化後)


[TOP] [ 前へ ] 連載記事 [ 次へ ]

nice!(0)  コメント(0) 
共通テーマ:趣味・カルチャー