Help needed on returning array of variable length from a library

I am writing an Arduino library to convert Pronto Hex infrared remote control codes to raw timings that can be sent with usual IR sending libraries.

Currently my convert() method returns a String. However, most users will want to send the converted code with an infrared remote control sending library. For that it would be better if we could access convertedRaw (an array of ints for the timings) rather than a String.

But C++ makes it really hard to return an array of variable length from a method.

So if someone would like to help, the code is at GitHub - probonopd/ProntoHex: Arduino library to convert Pronto Hex infrared remote control codes to raw timings that can be sent with usual IR sending libraries and I have opened a ticket at Access array of raw timings rather than a String · Issue #1 · probonopd/ProntoHex · GitHub

Thanks!

The usual way to solve that problem is to have the caller provide the buffer.

Which raises a new problem: how does the caller size the buffer?

One solution is to provide a maximum sized buffer. array in your convert method is a good example. You assume 80 entries will always be enough.

The other solution is to first query for the buffer size. This is an example...

#include <alloca.h>

int ProntoHex_convert(
    String & prontoDataStr,
    uint16_t buffer[],
    size_t & size )
{
  // If the caller wants to know what size buffer is needed
  if ( buffer == NULL )
  {
    size = 17;
  }
  // Otherwise, the caller wants the buffer filled with data
  else
  {
    // Fill buffer with data
  }
  return( 0 );
}

void setup() 
{
  String prontoDataStr;
  uint16_t * buffer;
  size_t size;

  // Query for the buffer size
  if ( ProntoHex_convert( prontoDataStr, NULL, size ) == 0 )
  {
    // Allocate a buffer
    buffer = (uint16_t*) alloca( size );

    // Ask for the buffer to be filled
    if ( ProntoHex_convert( prontoDataStr, buffer, size ) == 0 )
    {
      // Process the buffer
    }
  }
}

void loop() 
{
}

Thanks for your suggestions Coding Badly. Using a fixed length seems not very elegant, and adding so many lines of code as in your example would achieve the goal but seems confusing to me. Somewhere else I read "you can return a pointer to an array by specifying the array's name without an index" but I could not make that work so far - does that sound like a sensible solution and do you know how to do this?

The only way that can possibly work is if the pointer points to a global / static buffer or points to memory allocated from the heap (malloc; which has to be paired with free).

The problem with the first solution is that you are back to having a fixed size buffer.

The risk with the second solution is the same as for returning String: heap fragmentation and error recovery.

...adding so many lines of code...

Basically, you call convert twice with an alloca in between. (Or introduce a method that returns the buffer size. It is six of one half dozen of the other.)

Thanks for your help! (Makes me feel less stupid now since I was thinking I must be overlooking the obvious.)