Hello again,
First of all, sorry for the very long post
I managed to understand some things since last time. I think I might have found a way of making this work, but there is something I still can’t figure out.
What I’m doing in my module is initializing UART1 with the same commands in mios32_uart.c :
// TX MIDI1: P2.0
MIOS32_SYS_LPC_PINSEL(2, 0, 2);
MIOS32_SYS_LPC_PINMODE(2, 0, 2);
MIOS32_SYS_LPC_PINMODE_OD(2, 0, 1);
// RX MIDI1: P2.1 w/ pull-up enabled
MIOS32_SYS_LPC_PINSEL(2, 1, 2);
MIOS32_SYS_LPC_PINMODE(2, 1, 0);
Then I pre calculate the baudrate (copy/paste of mois32_uart. again), and store both fast and slow value :
[… copy from mios32_uart.c with baudrate 250000]
// Store for fast changes
dmx_br_diviserOptimal = diviserOptimal;
dmx_br_mulFracDivOptimal = mulFracDivOptimal;
dmx_br_dividerAddOptimal = dividerAddOptimal;
[… copy from mios32_uart.c with baurdate 40000]
// Store for fast changes
break_br_diviserOptimal = diviserOptimal;
break_br_mulFracDivOptimal = mulFracDivOptimal;
break_br_dividerAddOptimal = dividerAddOptimal;
So I can easily configure ports using dmx_br_ or break_br_
// Setup to DMX
DMX->LCR = 0x87; // 8 bits, no Parity, 2 stop bit, no break, DLAB=1
DMX->DLM = (dmx_br_diviserOptimal >> 8) & 0xff;
DMX->DLL = dmx_br_diviserOptimal & 0xff;
DMX->LCR = 0x03; // disable access to divisor latches
DMX->FDR = ((dmx_br_mulFracDivOptimal&0xf) << 4) | (dmx_br_dividerAddOptimal&0xf);
DMX->FCR = 0x07; // Enable and reset TX and RX FIFO
Then I configure the interrupt as in mios32_uart.c
DMX->IER = (1 << 1) | (1 << 0); // enable RBR and THRE (receive/transmit buffer) interrupt
MIOS32_IRQ_Install(DMX_IRQ_CHANNEL, MIOS32_IRQ_UART_PRIORITY);
As in Phil Taylor’s module
// Create timer to send DMX universe.
vSemaphoreCreateBinary(xDMXSemaphore);
xTaskCreate(TASK_DMX, (signed portCHAR *)“DMX”, configMINIMAL_STACK_SIZE, NULL, PRIORITY_TASK_DMX, NULL);
In the task, I copied Phil’s module, but using break_br_ variables to setup the port and send the break when in IDLE state
static void TASK_DMX(void *pvParameters)
{
portTickType xLastExecutionTime;
// Initialise the xLastExecutionTime variable on task entry
xLastExecutionTime = xTaskGetTickCount();
while( 1 ) {
vTaskDelayUntil(&xLastExecutionTime, 35 / portTICK_RATE_MS);
if (dmx_state==DMX_IDLE)
{
if (xSemaphoreTake(xDMXSemaphore, 10)==pdTRUE) { // Stop the universe from being changed while we are sending it.
// Setup to break Baudrate
DMX->LCR = 0x87; // 8 bits, no Parity, 2 stop bit, no break, DLAB=1
DMX->DLM = (break_br_diviserOptimal >> 8) & 0xff;
DMX->DLL = break_br_diviserOptimal & 0xff;
DMX->LCR = 0x03; // disable access to divisor latches
DMX->FDR = ((break_br_mulFracDivOptimal&0xf) << 4) | (break_br_dividerAddOptimal&0xf);
DMX->FCR = 0x07; // Enable and reset TX and RX FIFO
// break code
DMX->THR = 0x00;
// State
dmx_state=DMX_BREAK;
}}}}
And finally in the interrupt, I deal with end of transmissions (THRE) : If we were in DMX_BREAK state, I switch to DMX_SEND. If we are in DMX_SEND, I upadate the register with the next channel byte. Until there is no channel left, then switch to IDLE state, which will allow the task to send a new break and so on…
signed portBASE_TYPE x=pdFALSE;
DMX_IRQHANDLER_FUNC
{
u32 iir_intid = DMX->IIR & 0xe; // IIR will be released with this access
if( iir_intid == 0x2 ) { // IntId = 0x1 (THRE) End of transmission
// If we were sending break
if(dmx_state == DMX_BREAK) {
// Reset Channel
dmx_current_channel=0;
// Setup to DMX baudrate
DMX->LCR = 0x87; // 8 bits, no Parity, 2 stop bit, no break, DLAB=1
DMX->DLM = (dmx_br_diviserOptimal >> 8) & 0xff;
DMX->DLL = dmx_br_diviserOptimal & 0xff;
DMX->LCR = 0x03; // disable access to divisor latches
DMX->FDR = ((dmx_br_mulFracDivOptimal&0xf) << 4) | (dmx_br_dividerAddOptimal&0xf);
DMX->FCR = 0x07; // Enable and reset TX and RX FIFO
// start code
DMX->THR = 0x00;
// State
dmx_state=DMX_SENDING;
}
// If we were sending a channel
if(dmx_state == DMX_SENDING) {
// If not all channels sent
if( dmx_current_channel<DMX_UNIVERSE_SIZE ) {
// Get current channel byte
s32 b = DMX_GetChannel(dmx_current_channel);
// If unable to get channel byte
if( b < 0 ) {
// Send zero in case of doubt
b = 0x00;
}
// Transmit channel byte
DMX->THR = b;
// Next channel
dmx_current_channel++;
}
// All channels have been sent
else {
// State
dmx_state=DMX_IDLE;
xSemaphoreGiveFromISR(xDMXSemaphore,&x);
}
}
}
}
The program is running fine, with no hangs or error messages. But when I wire a dmx led bar to the uart, nothing expected happens (random blinking or blackout, but the bar says some DMX is entering, not sure if proper DMX though). I dont have an oscilloscope (but will probably be able to use one tomorrow). So I pluged a LED and it lighted and blinked rapidly, so something is going out of that UART ^^
My question is (after all this text ^^) how would one be sure that the UART pins are correctly configured ? I read in Phil’s module that they’re supposed to be push-pull outputs, but I couldn’t find how to check that on a LPC1769. Also I’m not sure I ‘copied’ right the part where the baudrate are set.
Edit : On the LPC17 core sheet, it says that J12 (MIDI Out 1) is : TXD1 / GND / 3.3V, that’s my main concern actually, as I am not sure it can match DMX+ / GND / DMX-
I know it’s a lot to read, probably not very clear, but if someone has a hint on how to check that (code-side), or knows better how to do pin configuration on a LPC17, I would be very happy 
I’ll continue my tests anyway, and and of course share my results with you when/if I succeed
Thanks in advance,
Poivrelec