5 years, 10 months ago.

How can I pass CircularBuffer as function parmeter?

I am trying to pass CircularBuffer as function parameter, but I fail miserably with class templates, please help :-)

bool function(CircularBuffer<class,int> *buf, char *line);

[Error] blah.h@40,40: wrong number of template arguments (1, should be at least 2)

Another try returns:

bool function(CircularBuffer<char, long unsigned int> *buf, char *line);
bool function(CircularBuffer<char, uint32_t> *buf, char *line);

[Error] blah.h@40,53: type/value mismatch at argument 2 in template parameter list for 'template<class T, long unsigned int BufferSize, class CounterType> class mbed::CircularBuffer'

I want to find a line of text from circular buffer and then pass it to parser for command processing.. maybe there is already a better way here to do that? :-)

Hi Tomasz,

Could you post your entire .cpp file for context? Thanks!

-Karen, team Mbed

posted by Karen Yen 27 Jun 2018

Hello Karen! :-) The file is rather big.. what I have is CyclicBuffer that gets filled from RX BLE UART at onWrite(), then at some point periodically I want to get commands to parse from that buffer.. so I would like to pass it into bool ReadLine(CyclicBuffer rx, char *command). If ReadLine returns True I should have command (a string line ended with \r\n) in *command, then I can use strcmp() to extract command and call some functions that would put results into TX CyclicBuffer and that guy would be again at some point in time periodically flushed into TX characteristics..

I don't really know on how to put that CyclicBuffer (pointer) as a function parameter due this templating stuff :-)

As for now I have to use global CyclicBuffers to skip that problem somehow.. but I would like to process several buffers that way (i.e. from UART and from BLE UART).. I could have stuff aggregated into CyclicBuffer and then in some point in time process its contents..

Also finding '\n' in CyclicBuffer seems a bit harsh because I need to pop all elements and check each one of them for '\n' occurance, then push them back if '\n' did not occur which means the command may not be complete yet..

Maybe I am using wrong approach to this and some better solution (like getopt() in Unix)exist already? :-)

Any hints wlecome :-)

posted by Tomasz CEDRO 27 Jun 2018

Below is an example that works for me now, I have two buffers for bleUart and USB Uart.. there may be more buffers for Ethernet etc. I would like to pass CirtularBuffer to bufBleUartRxReadLn() so it can search if there is a line of text ready for processing in the pointed buffer..

<<code>>> static char uartCommand[BUFSIZE];

void bleOnDataWritten(const GattWriteCallbackParams *params) { if ((bleUartService != NULL) && (params->handle == bleUartService->getTXCharacteristicHandle())) { static int i; for (i=0;i<params->len;i++) bufCBleUartRx.push(params->data[i]); BLE::Instance().gattServer().write(bleUartService->getRXCharacteristicHandle(), params->data, params->len, false); } }

void terminalBufferFlush(void) { static int i; static char c; if (uart.readable()){ while (c=uart.getc()){ bufCBleUartRx.push(c); printf("%c",c); } }

if (BLE::Instance().gap().getState().connected) { if (!bufCBleUartTx.empty()){ for (i=0;i<BLE_UART_CHUNKSIZE;i++){ bufCBleUartTx.pop(c); bleUartService->writeString(&c); printf("%c",c); } } } }

void terminalProcessing(void){ terminalParse(); terminalBufferFlush(); }

void terminalParse(void){ static int i; static char c; if (!(i=bufBleUartRxReadLn(uartCommand))) return; DEBUG("[TERMINAL] terminalParse(): found a command: %s (bytes %d length)\r\n", uartCommand, i); bufBleUartTxWrite(uartCommand,i); if (!strncmp(uartCommand,"termCOMMAND1\n", i) || !strncmp(uartCommand, "termCOMMAND1\r\n", i)){ allSomeFunction(char *resultstring, ...); bufBleUartTxWrite(termHelp,sizeof(resultstring)); } else { bufBleUartTxWrite(termHint,sizeof(termHint)); } }

int bufBleUartRxReadLn(char *line){ < HERE I WOULD LIKE TO PASS CIRCULARBUFFER POINTER static int i, j, size; size=bufCBleUartRx.size(); for (i=0;i<size;i++){ bufCBleUartRx.pop(line[i]); if (line[i]=='\n') return i+1; } bufReadLn_rollback: for (j=0;j<size;j++) bufCBleUartRx.push(line[j]); return 0; } <</code>

posted by Tomasz CEDRO 28 Jun 2018

whoops there is a typo in my reply above, and i am unable to edit it.. some bug on a website? :-(

posted by Tomasz CEDRO 28 Jun 2018

Hi Tomasz,

I'm currently looking to see how to get around the error. As for the comment editing not working, that is indeed a bug that our web team is currently working on to fix. Apologies for any inconveniences!

-Karen, team Mbed

posted by Karen Yen 28 Jun 2018

No worries, thank you Karen! :-)

posted by Tomasz CEDRO 28 Jun 2018

1 Answer

5 years, 9 months ago.

Hello Tomasz,

Apologies for the delayed response. So I believe that when you declare your function, you need to declare an integer as your buffer size. Taking from the example for the CircularBuffer class:

https://os.mbed.com/teams/mbed_example/code/mbed-os-example-circular-buffer/

#define BUF_SIZE    10     
CircularBuffer<char, BUF_SIZE> buf;

Therefore, your functions should be declared as:

#define BUF_SIZE    10
bool function(CircularBuffer<char, BUF_SIZE> *buf, char *line);
bool function(CircularBuffer<char, BUF_SIZE> *buf, char *line);

I was able to compile the code above without any error. Hope this helps!

-Karen, team Mbed

If this solved your question, please make sure to click the "Thanks" link below!