0

I want to create my own function in an existing library from Arduino/ESP8266, pass an empty array in case the user doesn't have any header.

//.h file
t_httpUpdate_return updateheader(WiFiClient& client, const String& url, const String& currentVersion = "", const String& header[][2] = {{}});

//.cpp file
HTTPUpdateResult ESP8266HTTPUpdate::updateheader(WiFiClient& client, const String& url, const String& currentVersion, const String& header[][2])
{
    HTTPClient http;
    http.begin(client,url);
    for (int i, i < sizeof(header), i++){
        http.addHeader(F(header[i][0]), header[i][1]);
    }
    return handleUpdate(http, currentVersion, false);
}

But I get the next error when I try to compiling:

C:\Users\myuser\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.7.1\libraries\ESP8266httpUpdate\src/ESP8266httpUpdate.h:125:143: error: declaration of 'header' as array of references
    
t_httpUpdate_return updateheader(WiFiClient& client, const String& url, const String& currentVersion = "", const String& header[][2] = {{}});
    
                                                                                                                                        ^
    
exit status 1
    Error compilando para la tarjeta NodeMCU 1.0 (ESP-12E Module).

I'm using ESP8266httpUpdate Library.

DrakoPD
  • 161
  • 1
  • 13
  • You can't create an array of references. Also, `header` is a pointer, so `sizeof(header)` will be either 4 or 8 depending on the target, – molbdnilo Jun 17 '20 at 21:12
  • What are you trying to pass to the function? could it be better to pass an `std::vector` or just a string? Arrays will decay into pointers when passed to a function explained [here](https://www.tutorialspoint.com/what-is-array-decay-in-cplusplus#:~:text=The%20loss%20of%20type%20and,is%20not%20the%20original%20one.). And is this by any change a 2D pointer array? – Dorian Jun 17 '20 at 21:13
  • @Dorian I want to pass something like `{{"content-type","plain/text"},{"Authorization","pass"} }` – DrakoPD Jun 17 '20 at 21:18

1 Answers1

1

Arrays of references are not allowed. Also, you can't constrain the size of the inner array like that.

Arrays can't be passed around as values, they basically decay to pointers when you pass them to another function. That also means you need to pass along the size of the array.

What you wrote: sizeof(header) is a bug - you got a C-style array as a function argument, the array decays to a pointer and sizeof(header) gives you the size of a pointer and not the length of the array!

I'd use a struct for the actual header, since you always want a size of 2 and then you only have to deal with a one-dimensional array:

struct HttpHeader {
    String name;
    String value;
};

t_httpUpdate_return updateheader(WiFiClient& client, const String& url,
        const String& currentVersion = "",
        const HttpHeader* headers, int headers_size)
{
    HTTPClient http;
    http.begin(client,url);

    for (int i = 0; i < headers_size; i++) {
        http.addHeader(F(headers[i].name), headers[i].value);
    }

    return handleUpdate(http, currentVersion, false);
}

// Calling it somewhere:
HttpHeader headers[] = { { String("Accept"), String("application/json") } };
updateheader(client, version, headers, 1);

Note that this means the array data lives in the stack of the calling function and the pointer becomes invalid once that function ends. But that's always the case when not using heap allocation.

Benjamin Maurer
  • 3,602
  • 5
  • 28
  • 49
  • No, because Arduino doesn't have vector library. – DrakoPD Jun 24 '20 at 18:26
  • I didn't realize that Arduino is a subset of C++, I have never worked with it. The updated version should work for you. – Benjamin Maurer Jun 25 '20 at 13:42
  • I got a new error: `no matching function for call to 'ESP8266HTTPUpdate::update(BearSSL::WiFiClientSecure&, const char [64], const char [2], HttpHeader [2], int)'` You can check the library that I want to edit here [Code on GitHub](https://github.com/esp8266/Arduino/tree/master/libraries/ESP8266httpUpdate) If you want to know more about it. – DrakoPD Jun 25 '20 at 21:42
  • Seriously? I'm not going to search through this library and image what you might have changed to get that error. The error says that it can't find the function you are trying to call. Post the code of the function you defined, post the code where you call it, show us how you build it. – Benjamin Maurer Jun 26 '20 at 10:53
  • Well, you don't to search, is because your example is not correctly defined, you forgot `ESP8266HTTPUpdate::`, because is a class, also you didn't specify `.h` and `.cpp` file, so, I don't know what exactly you did. But I will edit my question for you. – DrakoPD Jun 27 '20 at 01:08
  • Never mind, its worked, it was the declaration of the struct, must be in the `.h` file, but I edited your answer to fix the mistakes in your code – DrakoPD Jun 27 '20 at 01:56
  • For reasons that I don't know F() function give me an error: `note: in expansion of macro 'PSTR' #define F(string_literal) (FPSTR(PSTR(string_literal)))` and `note: in expansion of macro 'F'`, so I just removed, its not necesary, only help to save space on RAM – DrakoPD Jun 27 '20 at 02:13
  • I rejected your edit, because your question was "How do I pass an array to a function". This is supposed to be a generally helpful QA site. Making it about how to change a specific function in a specific library to your specific liking is not useful. I showed the general way to solve the problem - how you incorporate this in your code is your task. And if you have further, new problems, then please open a new question for them, as Questions and Answers are supposed to be specific to one problem. – Benjamin Maurer Jun 27 '20 at 11:14
  • Ok, but you didn't specify the files (as I did), because in my question I said that is a library, and is a class (also the tags said that is Arduino, I will add it to the tittle). Your answer should be directed to my question, not the general public. I had to spend couple of hours trying to figure how to implement your code to me, because I got many errors and I'm not an expert in this. And I told you that `F()` function give an error with your method, remove it. Arduino doesn't support all functions of C++ and runs on limited hardware, you must keep that in mind. – DrakoPD Jun 27 '20 at 17:59
  • Also, in your example `String("Accept"), String("application/json")` don't use this as example, ESP8266httpUpdate library doesn't support JSON object, better use `authorization` or other thing. Arduino by default doesn't support JSON. – DrakoPD Jun 27 '20 at 18:29