MAX3100, an external serial device to add additional serial ports via SPI
Dependents: FLIGHT_CONTROL_AND_COMMUNICATIONS_SYSTEM
Revision 1:46c8c60e744a, committed 2011-01-17
- Comitter:
- AjK
- Date:
- Mon Jan 17 01:14:16 2011 +0000
- Parent:
- 0:055897ab699b
- Child:
- 2:2a49171453d5
- Commit message:
- 1.1 See ChangeLog.h
Changed in this revision
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/ChangeLog.h Mon Jan 17 01:14:16 2011 +0000 @@ -0,0 +1,34 @@ +/* + Copyright (c) 2011 Andy Kirkham + + Permission is hereby granted, free of charge, to any person obtaining a copy + of this software and associated documentation files (the "Software"), to deal + in the Software without restriction, including without limitation the rights + to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + copies of the Software, and to permit persons to whom the Software is + furnished to do so, subject to the following conditions: + + The above copyright notice and this permission notice shall be included in + all copies or substantial portions of the Software. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + THE SOFTWARE. +*/ + +/* + +1.1 17/01/2011 + Added this file. + Altered the way interrupts are disabled. Previously __disable_irq()/__enable_irq() + was used. However, this is somewhat "heavy handed". So we added in an _irqMask + property which allows us to just enable/disable the specific InterruptIn used. + +1.0 16/01/2011 + Initial release. + +/* \ No newline at end of file
--- a/MAX3100.cpp Sun Jan 16 18:27:44 2011 +0000 +++ b/MAX3100.cpp Mon Jan 17 01:14:16 2011 +0000 @@ -52,7 +52,8 @@ _spi->frequency(MAX3100_SPI_FREQ); } - if (irq != NC) { + if (irq != NC) { + irqMask(irq); _irq = new InterruptIn(irq); _irq->mode(PullUp); topic_1498(irq); @@ -100,49 +101,49 @@ void MAX3100::baud(int baudrate) { - __disable_irq(); + irqDisable(); config &= ~(0xf); config |= (baudrate & 0xf); config_write(config); - __enable_irq(); + irqEnable(); } void MAX3100::enableRxIrq(void) { - __disable_irq(); + irqDisable(); config &= ~MAX3100_RM(1); config |= MAX3100_RM(1); config_write(config); - __enable_irq(); + irqEnable(); } void MAX3100::disableRxIrq(void) { - __disable_irq(); + irqDisable(); config &= ~MAX3100_RM(1); config_write(config); - __enable_irq(); + irqEnable(); } void MAX3100::enableTxIrq(void) { - __disable_irq(); + irqDisable(); config &= ~MAX3100_TM(1); config |= MAX3100_TM(1); config_write(config); - __enable_irq(); + irqEnable(); } void MAX3100::disableTxIrq(void) { - __disable_irq(); + irqDisable(); config &= ~MAX3100_TM(1); config_write(config); - __enable_irq(); + irqEnable(); } int @@ -163,7 +164,7 @@ // Function is non-interruptable by the MAX3100 class // to avoid SPI bus contention between writing a byte // in user context (here) and IRQ context. - __disable_irq(); + irqDisable(); conf = config_read(); @@ -184,7 +185,7 @@ if (tx_buffer_in == tx_buffer_out) tx_buffer_full = true; } - __enable_irq(); + irqEnable(); return 1; } @@ -261,16 +262,16 @@ { switch(i) { case 1: - __disable_irq(); + irqDisable(); config &= ~(1 << 6); config_write(config); - __enable_irq(); + irqEnable(); break; case 2: - __disable_irq(); + irqDisable(); config |= (1 << 6); config_write(config); - __enable_irq(); + irqEnable(); break; } } @@ -284,6 +285,53 @@ } return count & 1; } + +void +MAX3100::irqDisable(void) +{ + if (_irqMask0) LPC_GPIOINT->IO0IntEnF &= ~_irqMask0; + if (_irqMask2) LPC_GPIOINT->IO2IntEnF &= ~_irqMask2; +} + +void +MAX3100::irqEnable(void) +{ + if (_irqMask0) LPC_GPIOINT->IO0IntEnF |= _irqMask0; + if (_irqMask2) LPC_GPIOINT->IO2IntEnF |= _irqMask2; +} + +void +MAX3100::irqMask(PinName p) +{ + _irqMask0 = _irqMask2 = 0; + + switch( p ) { + case p5: _irqMask0 = (1UL << 9); break; + case p6: _irqMask0 = (1UL << 8); break; + case p7: _irqMask0 = (1UL << 7); break; + case p8: _irqMask0 = (1UL << 6); break; + case p9: _irqMask0 = (1UL << 0); break; + case p10: _irqMask0 = (1UL << 1); break; + case p11: _irqMask0 = (1UL << 18); break; + case p12: _irqMask0 = (1UL << 17); break; + case p13: _irqMask0 = (1UL << 15); break; + case p14: _irqMask0 = (1UL << 16); break; + case p15: _irqMask0 = (1UL << 23); break; + case p16: _irqMask0 = (1UL << 24); break; + case p17: _irqMask0 = (1UL << 25); break; + case p18: _irqMask0 = (1UL << 26); break; + case p21: _irqMask2 = (1UL << 5); break; + case p22: _irqMask2 = (1UL << 4); break; + case p23: _irqMask2 = (1UL << 3); break; + case p24: _irqMask2 = (1UL << 2); break; + case p25: _irqMask2 = (1UL << 1); break; + case p26: _irqMask2 = (1UL << 0); break; + case p27: _irqMask0 = (1UL << 11); break; + case p28: _irqMask0 = (1UL << 10); break; + case p29: _irqMask0 = (1UL << 5); break; + case p30: _irqMask0 = (1UL << 4); break; + } +} void MAX3100::topic_1498(PinName p) {
--- a/MAX3100.h Sun Jan 16 18:27:44 2011 +0000 +++ b/MAX3100.h Mon Jan 17 01:14:16 2011 +0000 @@ -112,6 +112,11 @@ int _device; int _parity; + uint32_t _irqMask0, _irqMask2; + + void irqDisable(void); + void irqEnable(void); + virtual int _putc(int c) { return putc(c); } virtual int _getc() { return getc(); } @@ -143,7 +148,7 @@ // calculate byte parity. int parityCal(uint8_t c); - + // http://mbed.org/forum/bugs-suggestions/topic/1498 void topic_1498(PinName p); @@ -290,6 +295,13 @@ */ void flushRxBuffer(void) { rx_buffer_in = rx_buffer_out = 0; rx_buffer_full = false; } + /** irqMask + * Setup the mask for enable/disable interrupts. + * @see example3.h + * @param PinName p The InterruptIn pin. + */ + void irqMask(PinName p); + /** attach_cs * Attach a C style callback function pointer. Used if an external function * is controlling the chip CS line. @@ -303,7 +315,9 @@ * @param method The method within the object to call. */ template<class T> - void attach_cs(T* item, void (T::*method)(int, int)) { _cs_obj = (MAX3100Dummy *)item; _cs_method = (void (MAX3100Dummy::*)(int, int))method; } + void attach_cs(T* item, void (T::*method)(int, int)) { + _cs_obj = (MAX3100Dummy *)item; _cs_method = (void (MAX3100Dummy::*)(int, int))method; + } };
--- a/example1.h Sun Jan 16 18:27:44 2011 +0000 +++ b/example1.h Mon Jan 17 01:14:16 2011 +0000 @@ -60,7 +60,6 @@ while (1) { if (pc.readable()) { int c = pc.getc(); - while (!max.writable()); max.putc(c); } if (max.readable()) {
--- a/example2.h Sun Jan 16 18:27:44 2011 +0000 +++ b/example2.h Mon Jan 17 01:14:16 2011 +0000 @@ -79,16 +79,14 @@ max2->enableTxIrq(); max1->printf("\nHello World.\n"); - max2->printf("\nHello World.\n"); + //max2->printf("\nHello World.\n"); // Any byte received on the "USB serial port" is sent to both MAX3100 devices. // Any byte received by a MAX3100 device is sent to the "USB serial port". while (1) { if (pc.readable()) { int c = pc.getc(); - while (!max1->writable()); - max1->putc(c); - while (!max2->writable()); + max1->putc(c); max2->putc(c); } if (max1->readable()) {
--- a/example3.h Sun Jan 16 18:27:44 2011 +0000 +++ b/example3.h Mon Jan 17 01:14:16 2011 +0000 @@ -123,6 +123,7 @@ max[index]->enableRxIrq(); max[index]->enableTxIrq(); max[index]->attach_cs(&address, &MAX3100_Addr::cs_select); + max[index]->irqMask(p12); // Tell objects where shared InterruptIn is. } // Connect the interrupt signal. @@ -135,7 +136,6 @@ int c = pc.getc(); for (index = 0; index < 8; index++) { if (max[index] != (MAX3100 *)NULL) { - while (!max[index]->writable()); max[index]->putc(c); } }