LPC1114FN28で同一ポート群から別々にデジタル出力する場合に出力波形が乱れることがあります。この現象を確認するためのテストプログラムです。
LPC1114FN28 でのデジタル出力について
LPC1114FN28でデジタル出力をする場合、同一ポート群に対して、個別出力をすると他方の出力に影響を与えます。
<サンプルプログラムの説明>
PIO1_xのポート群(dp13(PIO1_4),dp14(PIO1_5))で確認しました
Tickerで0.1ms周期割り込みでレベル反転(dp14)させ、main()でdp13から固定レベル出力させます。
main()でLo出力しているとき、割り込みで出力させているパルスが乱れます。
main()でHi出力させているときは、パルスは乱れません。
プログラムの 19行目の"NG_LEVEL"define定義を無効にするとこのプログラムになります。
dp13(PIO1_4)をdp1(PIO0_8)の別ポート群にするとパルスは乱れません。
プログラムの18行目の"NG_PORT"define定義を無効にするとこのプログラムになります。
LPC1768(青mbed)では、上記の様な現象は発生しません(P2xポート群(P21(P2.5),P22(P2.4)で確認)
プログラムの17行目の"LPC1114FN28"define定義を無効にして、コンパイラの設定をLPC1768にするとこのプログラムになります。
main.cpp@1:bf75eed34e82, 2013-10-28 (annotated)
- Committer:
- suupen
- Date:
- Mon Oct 28 12:10:33 2013 +0000
- Revision:
- 1:bf75eed34e82
- Parent:
- 0:01c0ed9b80c5
I described a bug workaround for this problem.
;
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
suupen | 0:01c0ed9b80c5 | 1 | /* |
suupen | 0:01c0ed9b80c5 | 2 | LPC1114FN28でデジタル出力をする場合、同一ポート群に対して、個別出力をすると他方の出力に影響を与えます。 |
suupen | 0:01c0ed9b80c5 | 3 | |
suupen | 0:01c0ed9b80c5 | 4 | <サンプルプログラムの説明> |
suupen | 0:01c0ed9b80c5 | 5 | PIO1_xのポート群(dp13(PIO1_4),dp14(PIO1_5))で確認 |
suupen | 0:01c0ed9b80c5 | 6 | Tickerで0.1ms周期割り込みでレベル反転(dp14)させ、main()でdp13から固定レベル出力させます。 |
suupen | 0:01c0ed9b80c5 | 7 | main()でLo出力しているとき、割り込みで出力させているパルスが乱れます。 |
suupen | 0:01c0ed9b80c5 | 8 | |
suupen | 0:01c0ed9b80c5 | 9 | main()でHi出力させているときは、パルスは乱れません。 |
suupen | 0:01c0ed9b80c5 | 10 | dp13(PIO1_4)をdp1(PIO0_8)の別ポート群にするとパルスは乱れません。 |
suupen | 1:bf75eed34e82 | 11 | mainでのパルス出力を割り込み禁止にするとパルスは乱れません。 |
suupen | 1:bf75eed34e82 | 12 | |
suupen | 1:bf75eed34e82 | 13 | <結論> |
suupen | 1:bf75eed34e82 | 14 | 割り込みとmainの双方で同一ポート群へのデジタル出力をすると出力レベルが異常になる場合がある。 |
suupen | 1:bf75eed34e82 | 15 | これは、ポート出力処理のbit演算でメモリからの読み出し、書き込みが重複するためと思われる。 |
suupen | 1:bf75eed34e82 | 16 | 回避方法は、mainルーチンでのデジタル出力時に割り込み禁止にすること。 |
suupen | 1:bf75eed34e82 | 17 | |
suupen | 0:01c0ed9b80c5 | 18 | |
suupen | 0:01c0ed9b80c5 | 19 | LPC1768(青mbed)では、上記の様な現象は発生しません(P2xポート群(P21(P2.5),P22(P2.4)で確認) |
suupen | 1:bf75eed34e82 | 20 | |
suupen | 1:bf75eed34e82 | 21 | 131028 mainでの割り込みと結論を追記 |
suupen | 0:01c0ed9b80c5 | 22 | */ |
suupen | 0:01c0ed9b80c5 | 23 | |
suupen | 0:01c0ed9b80c5 | 24 | #include "mbed.h" |
suupen | 0:01c0ed9b80c5 | 25 | |
suupen | 0:01c0ed9b80c5 | 26 | #define LPC1114FN28 // 無効時LPC1768設定になります |
suupen | 0:01c0ed9b80c5 | 27 | #define NG_PORT // 無効時、mainでの出力を別ポート群にします |
suupen | 0:01c0ed9b80c5 | 28 | #define NG_LEVEL // 無効時、mainでの出力をHiにします |
suupen | 1:bf75eed34e82 | 29 | //#define OK_IRQ // 有効時mainでの出力時に割り込み禁止にする(波形の乱れは無くなる) |
suupen | 0:01c0ed9b80c5 | 30 | |
suupen | 0:01c0ed9b80c5 | 31 | #ifdef LPC1114FN28 |
suupen | 0:01c0ed9b80c5 | 32 | |
suupen | 0:01c0ed9b80c5 | 33 | #ifdef NG_PORT |
suupen | 0:01c0ed9b80c5 | 34 | DigitalOut out(dp13); |
suupen | 0:01c0ed9b80c5 | 35 | #else //~NG_PORT |
suupen | 0:01c0ed9b80c5 | 36 | DigitalOut out(dp1); |
suupen | 0:01c0ed9b80c5 | 37 | #endif // NG_PORT |
suupen | 0:01c0ed9b80c5 | 38 | |
suupen | 0:01c0ed9b80c5 | 39 | DigitalOut test(dp14); |
suupen | 0:01c0ed9b80c5 | 40 | |
suupen | 0:01c0ed9b80c5 | 41 | #else // ~LPC1114FN28 (LPC1768) |
suupen | 0:01c0ed9b80c5 | 42 | DigitalOut out(p22); |
suupen | 0:01c0ed9b80c5 | 43 | DigitalOut test(p21); |
suupen | 0:01c0ed9b80c5 | 44 | #endif // LPC1114FN28 |
suupen | 0:01c0ed9b80c5 | 45 | |
suupen | 0:01c0ed9b80c5 | 46 | Ticker timer; |
suupen | 0:01c0ed9b80c5 | 47 | |
suupen | 0:01c0ed9b80c5 | 48 | void attime(){ |
suupen | 0:01c0ed9b80c5 | 49 | test = !test; |
suupen | 0:01c0ed9b80c5 | 50 | } |
suupen | 0:01c0ed9b80c5 | 51 | |
suupen | 0:01c0ed9b80c5 | 52 | |
suupen | 0:01c0ed9b80c5 | 53 | int main() { |
suupen | 0:01c0ed9b80c5 | 54 | timer.attach_us(&attime, 100); |
suupen | 0:01c0ed9b80c5 | 55 | |
suupen | 0:01c0ed9b80c5 | 56 | |
suupen | 0:01c0ed9b80c5 | 57 | |
suupen | 0:01c0ed9b80c5 | 58 | while(1) { |
suupen | 0:01c0ed9b80c5 | 59 | #ifdef NG_LEVEL |
suupen | 1:bf75eed34e82 | 60 | #ifdef OK_IRQ |
suupen | 1:bf75eed34e82 | 61 | __disable_irq(); // Disable Interrupts |
suupen | 1:bf75eed34e82 | 62 | #endif // OK_IRQ |
suupen | 0:01c0ed9b80c5 | 63 | out = 0; |
suupen | 1:bf75eed34e82 | 64 | #ifdef OK_IRQ |
suupen | 1:bf75eed34e82 | 65 | __enable_irq(); // Enable Interrupts |
suupen | 1:bf75eed34e82 | 66 | #endif // OK_IRQ |
suupen | 0:01c0ed9b80c5 | 67 | #else // ~NG_LEVEL |
suupen | 0:01c0ed9b80c5 | 68 | out = 1; |
suupen | 0:01c0ed9b80c5 | 69 | #endif // NG_LEVEL |
suupen | 0:01c0ed9b80c5 | 70 | } |
suupen | 0:01c0ed9b80c5 | 71 | } |
suupen | 0:01c0ed9b80c5 | 72 |