Trying to increase the TX buffer of a four port serial object.
Duane Degn
Posts: 10,588
Lately I've been adapting Tim Moore's four port serial object to my needs. I have several versions with various RX sizes. See this thread:
http://forums.parallax.com/showthread.php?129714-Tim-Moore-s-pcFullDuplexSerial4FC-with-larger-(512-byte)-rx-buffer
If any of you use Tim's object, I'd suggest switching to the 128 byte buffer version. You get twice the RX buffer at the cost of a few extra longs in code size.
My latest attempt is to increase one of the TX buffers from 16 bytes to 512 bytes. I plan to use the increased TX buffer with a Emic text to speech module. I don't want the main program loop to have to wait for the Emic.
In my initial attempt I decided to hard code the port using the larger TX buffer. I chose port 3. I added this to the init method.
I added emicBuffer after the cog image.
The three other tx buffers remain in the same area of hub RAM as the cog image.
It can be hard to tell what variables are being used within the cog and which are used in the hub. I thought I had figured this out. tx_buffer, tx_buffer1, etc are used as hub locations. txdata is used within the cog.
These tx buffers don't need to be located within the cog image.
I changed the start method from
I''ve only included the tx variables in these code pieces.
I'm pretty sure I don't need to change anything else in the start method.
I've also changed the tx method from
I also made changes in the PASM section. I'll use port 2 to show what the original code was.
Am I missing something? I'm attaching my test code. Sorry, but it's a mess. It had be used to test XBees so a lot of the Emic variables have XBee names.
I plan to use the Emic's Busy pin as a CTS pin. For now I have CTS disabled. I've been using this code with a Prop Plug connected where the Emic's "Sin" pin will be.
This is the output to the debug terminal
[code]
count[0] = 5876
count[1] = 3828
count[2] = 4340
count[3] = 4852
count[4] = 6024
count[5] = 2
count[6] = 0
count[7] = 7228
count[8] = 7236
count[9] = 7664
count[10] = 7670
count[11] = 0
count[12] = 0
count[13] = 2
c tx_head&tail = 0, 0
EmptyBuffer localBufferIndex = 0<$0D>
CheckBuffer rxFlag[0] = 0, oldRxFlag[0] = 0<$0D>
result = 0<$0D>
d tx_head&tail = 0, 0
c tx_head&tail = 0, 0
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
d tx_head&tail = 0, 0
1a tx_head&tail = 37, 2
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
1b tx_head&tail = 37, 8
2a tx_head&tail = 195, 13
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
2b tx_head&tail = 195, 18
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
6a tx_head&tail = 358, 32
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
9b t
http://forums.parallax.com/showthread.php?129714-Tim-Moore-s-pcFullDuplexSerial4FC-with-larger-(512-byte)-rx-buffer
If any of you use Tim's object, I'd suggest switching to the 128 byte buffer version. You get twice the RX buffer at the cost of a few extra longs in code size.
My latest attempt is to increase one of the TX buffers from 16 bytes to 512 bytes. I plan to use the increased TX buffer with a Emic text to speech module. I don't want the main program loop to have to wait for the Emic.
In my initial attempt I decided to hard code the port using the larger TX buffer. I chose port 3. I added this to the init method.
emicPort := 3
I added emicBuffer after the cog image.
tx_buffer 'overlay tx variables over txbuffer txdata long 0 ' DWD transmit buffers moved but are txbits long 0 ' are still the same size txcnt long 0 txdata1 long 0 tx_buffer1 'overlay tx variables over txbuffer txbits1 long 0 txcnt1 long 0 txdata2 long 0 txbits2 long 0 tx_buffer2 'overlay tx variables over txbuffer txcnt2 long 0 txdata3 long 0 txbits3 long 0 txcnt3 long 0 'overlay tx variables over txbuffer tx_buffer3 long 0 long 0 long 0 long 0 ' DWD group bytes together. rxchar byte 0 ' DWD within cog and by rxcheck method rxchar1 byte 0 rxchar2 byte 0 rxchar3 byte 0 ' FIT emicBuffer long 128
The three other tx buffers remain in the same area of hub RAM as the cog image.
It can be hard to tell what variables are being used within the cog and which are used in the hub. I thought I had figured this out. tx_buffer, tx_buffer1, etc are used as hub locations. txdata is used within the cog.
These tx buffers don't need to be located within the cog image.
I changed the start method from
txbuff_tail_ptr := txbuff_ptr := @tx_buffer txbuff_tail_ptr1 := txbuff_ptr1 := @tx_buffer1 txbuff_tail_ptr2 := txbuff_ptr2 := @tx_buffer2 txbuff_tail_ptr3 := txbuff_ptr3 := @tx_buffer3 tx_head_ptr := @tx_head tx_head_ptr1 := @tx_head1 tx_head_ptr2 := @tx_head2 tx_head_ptr3 := @tx_head3 tx_tail_ptr := @tx_tail tx_tail_ptr1 := @tx_tail1 tx_tail_ptr2 := @tx_tail2 tx_tail_ptr3 := @tx_tail3to
txbuff_tail_ptr := txbuff_ptr := @tx_buffer txbuff_tail_ptr1 := txbuff_ptr1 := @tx_buffer1 txbuff_tail_ptr2 := txbuff_ptr2 := @tx_buffer2 txbuff_tail_ptr3 := txbuff_ptr3 := @emicBuffer ' ********* changed ************ tx_head_ptr := @tx_head tx_head_ptr1 := @tx_head1 tx_head_ptr2 := @tx_head2 tx_head_ptr3 := @tx_head3 tx_tail_ptr := @tx_tail tx_tail_ptr1 := @tx_tail1 tx_tail_ptr2 := @tx_tail2 tx_tail_ptr3 := @tx_tail3
I''ve only included the tx variables in these code pieces.
I'm pretty sure I don't need to change anything else in the start method.
I've also changed the tx method from
PUB tx(port,txbyte) '' Send byte (may wait for room in buffer) if port > 3 abort repeat until (long[@tx_tail][port] <> (long[@tx_head][port] + 1) & $F) byte[@tx_buffer][(port<<4)+long[@tx_head][port]] := txbyte long[@tx_head][port] := (long[@tx_head][port] + 1) & $F if long[@rxtx_mode][port] & NOECHO rx(port)to
PUB tx(port,txbyte) '' Send byte (may wait for room in buffer) if port > 3 abort if port == emicPort repeat until (long[@tx_tail][port] <> (long[@tx_head][port] + 1) & $1FF) byte[@emicBuffer][long[@tx_head][port]] := txbyte long[@tx_head][port] := (long[@tx_head][port] + 1) & $1FF if long[@rxtx_mode][port] & NOECHO rx(port) else repeat until (long[@tx_tail][port] <> (long[@tx_head][port] + 1) & $F) byte[@tx_buffer][(port<<4)+long[@tx_head][port]] := txbyte long[@tx_head][port] := (long[@tx_head][port] + 1) & $F if long[@rxtx_mode][port] & NOECHO rx(port)I believe the (port<<4) is used to multiply the port by 16 in order to use the correct 16 byte tx buffer. Since the emicBuffer starts at the beginning, I don't need to shift the port number.
I also made changes in the PASM section. I'll use port 2 to show what the original code was.
transmit2 jmpret txcode2,rxcode3 'run a chunk of receive code, then return {282,84}txcts2 test ctsmask2,ina wc 'if flow-controlled don't send rdlong t1,tx_head_ptr2 cmp t1,tx_tail2 wz ctsi2 if_z jmp #transmit2 'may be patched to if_z_or_c or if_z_or_nc rdbyte txdata2,txbuff_tail_ptr2 add tx_tail2,#1 and tx_tail2,#$0F wz wrlong tx_tail2,tx_tail_ptr2 if_z mov txbuff_tail_ptr2,txbuff_ptr2 'reset tail_ptr if we wrapped if_nz add txbuff_tail_ptr2,#1 'otherwise add 1 {292,94} jmpret txcode2,rxcode3 shl txdata2,#2 or txdata2,txbitor 'ready byte to transmit mov txbits2,#11 mov txcnt2,cnt txbit2 shr txdata2,#1 wc txout2 muxc outa,txmask2 'maybe patched to muxnc dira,txmask add txcnt2,bit_ticks2 'ready next cnt :wait2 jmpret txcode2,rxcode3 'run a chunk of receive code, then return mov t1,txcnt2 'check if bit transmit period done {302,104} sub t1,cnt cmps t1,#0 wc if_nc jmp #:wait2 djnz txbits2,#txbit2 'another bit to transmit? txjmp2 jmp ctsi2 'byte done, transmit next byteHere is port 3's code with my changes.
transmit3 jmpret txcode3,rxcode 'run a chunk of receive code, then return txcts3 test ctsmask3,ina wc 'if flow-controlled dont send rdlong t1,tx_head_ptr3 cmp t1,tx_tail3 wz ctsi3 if_z jmp #transmit3 'may be patched to if_z_or_c or if_z_or_nc {312,114} rdbyte txdata3,txbuff_tail_ptr3 add tx_tail3,#1 and tx_tail3,#$1FF wz ' ******* changed *************** wrlong tx_tail3,tx_tail_ptr3 if_z mov txbuff_tail_ptr3,txbuff_ptr3 'reset tail_ptr if we wrapped if_nz add txbuff_tail_ptr3,#1 'otherwise add 1 jmpret txcode3,rxcode shl txdata3,#2 or txdata3,txbitor 'ready byte to transmit mov txbits3,#11 {322,124} mov txcnt3,cnt txbit3 shr txdata3,#1 wc txout3 muxc outa,txmask3 'maybe patched to muxnc dira,txmask add txcnt3,bit_ticks3 'ready next cnt {128}local_wait3 jmpret txcode3,rxcode 'run a chunk of receive code, then return rx_buffer3 mov t1,txcnt3 'check if bit transmit period done sub t1,cnt cmps t1,#0 wc if_nc jmp #local_wait3 djnz txbits3,#txbit3 'another bit to transmit? {332,6}txjmp3 jmp ctsi3 'byte done, transmit next byteI just changed when txbuff_tail_ptr3 gets reset from $F (15) to $1FF (511).
Am I missing something? I'm attaching my test code. Sorry, but it's a mess. It had be used to test XBees so a lot of the Emic variables have XBee names.
I plan to use the Emic's Busy pin as a CTS pin. For now I have CTS disabled. I've been using this code with a Prop Plug connected where the Emic's "Sin" pin will be.
This is the output to the debug terminal
[code]
count[0] = 5876
count[1] = 3828
count[2] = 4340
count[3] = 4852
count[4] = 6024
count[5] = 2
count[6] = 0
count[7] = 7228
count[8] = 7236
count[9] = 7664
count[10] = 7670
count[11] = 0
count[12] = 0
count[13] = 2
c tx_head&tail = 0, 0
EmptyBuffer localBufferIndex = 0<$0D>
CheckBuffer rxFlag[0] = 0, oldRxFlag[0] = 0<$0D>
result = 0<$0D>
d tx_head&tail = 0, 0
c tx_head&tail = 0, 0
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
d tx_head&tail = 0, 0
1a tx_head&tail = 37, 2
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
1b tx_head&tail = 37, 8
2a tx_head&tail = 195, 13
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
2b tx_head&tail = 195, 18
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
6a tx_head&tail = 358, 32
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
EmptyBuffer localBufferIndex = 3<$0D>
CheckBuffer rxFlag[3] = 0, oldRxFlag[3] = 0<$0D>
result = 0<$0D>
9b t
Comments
I'm marking this thread "solved" for now. If I the code still doesn't work after I make some obvious changes I might switch it back to "unsolved."
One of the problems is
should be
I made the same mistake when I was working on the rx buffers.
Sorry if I wasted anyone's time.
Duane