DaveO
April 2, 2012, 2:18pm
1
I have the following function which sends text to a php script. But the php script only gets the first word of the sentence.
How do I convert the LogTxt to something that the php will receive as a sentence ?
eg : sending : this is a line, of data, 1,2,3
void LogItWebC(char* LogTxt){
if (client.connect(myserver, 80)) {
Serial.println("connected");
client.print("GET http://www.AAA.co.za/serveit.php?data=");
client.print(LogTxt);
client.println(" HTTP/1.1");
client.println("Host: www.AAA.co.za");
client.println();
delay(250);
client.stop();
Serial.println(LogTxt);
Serial.println("disconnected");
Serial.println("==================");
}
else {
Serial.println("connection failed");
Serial.println("==================");
}
}
system
April 2, 2012, 2:38pm
2
You need to replace certain characters, like space, with different characters. Space becomes %20. You can look at how php encodes URLs and have the Arduino encode the same characters the same way.
DaveO
April 2, 2012, 2:57pm
3
do you know if there is an available function that can do this without me needing to write code for it ?
system
April 2, 2012, 3:42pm
5
Feeling lazy today, are we?
unsigned char specials[] = " "; /* String containing chars you want encoded */
static unsigned char hex_digit(unsigned char c)
{ return "01234567890ABCDEF"[c & 0x0F];
}
unsigned char *urlencode(unsigned char *dst,unsigned char *src)
{ unsigned char c,*d = dst;
while (c = *src++)
{ if (strchr(specials,c))
{ *d++ = '%';
*d++ = hex_digit(c >> 4);
*d++ = hex_digit(c);
}
else *d++ = c;
}
return dst;
}
Edit: added declaration of c
DaveO
April 2, 2012, 4:56pm
6
OK. So if I get this right, I add the code sample you kindly supplied below my existing function, and change the specials value to :
unsigned char specials[] = "§_DISCOURSE_HOISTED_CODE_0_§+,/:;=?@ <>#%{}|\^~[]`"; /* String containing chars you want encoded */
static unsigned char hex_digit(unsigned char c)
{ return "01234567890ABCDEF"[c & 0x0F];
}
unsigned char *urlencode(unsigned char *dst,unsigned char *src)
and in my function I add :
void LogItWebC(char* LogTxt){
char URLed = urlencode(LogTxt);
then I get an error on compile :
Invalid conversion from 'char*' to 'unsigned char*'
I have only a basic understanding of why this is happening, but not of how to solve it.
Also, the urlencode function appears to require 2 variables passed to it ( dst and src ). What are they ? I only have 1 char ( LogTxt ) that I want encoded.
system
April 2, 2012, 5:08pm
7
Invalid conversion from 'char*' to 'unsigned char*'
I have only a basic understanding of why this is happening, but not of how to solve it.
Change all the unsigned chars to signed chars. That is, simply removed the unsigned keyword.
I only have 1 char ( LogTxt ) that I want encoded.
The encoded string will be longer than the original string, so you need to define and supply a place to store the encoded string.
DaveO
April 2, 2012, 5:12pm
8
char specials[] = "§_DISCOURSE_HOISTED_CODE_0_§+,/:;=?@ <>#%{}|~[]`"; ///* String containing chars you want encoded */
static char hex_digit(char c)
{ return "01234567890ABCDEF"[c & 0x0F];
}
char* urlencode(char* dst,char* src)
{ char *d = dst;
while (c = *src++)
{ if (strchr(specials,c))
{ *d++ = '%';
*d++ = hex_digit(c >> 4);
*d++ = hex_digit(c);
}
else *d++ = c;
}
return dst;
}
'c' was not declared in this scope
system
April 2, 2012, 5:20pm
9
char* urlencode(char* dst,char* src)
{ char *d = dst;
char c;
DaveO
April 2, 2012, 5:25pm
10
Many Thanks
Now the (hopefully) last issue is : what should be passed to :
char* urlencode(char* dst,char* src)
as it looks like it is expecting 2 variables to be passed to it.
system
April 2, 2012, 5:37pm
11
void LogItWebC(char* LogTxt)
{
char encodedTxt[120];
urlencode(encodedTxt, LogTxt);
.
.
.
// client.print(LogTxt);
client.print(encodedTxt);
.
.
.
}
system
April 2, 2012, 5:39pm
12
PaulS first: Yuppers, I should have caught that before posting and you spotted it before I could correct. Thank you.
Dave next: You'll want a buffer to convert into and output from. For sake of discussion, let's call it 'buffer' and make it 80 chars wide:
char buffer[80];
will probably do the job. Now all that's needed is to recode to
client.print(urlencode(buffer,LogTxt));
to output that line in a urlencoded form.
DaveO
April 2, 2012, 5:44pm
13
Many Thanks all. ALMOST there.
now the line :
client.print(urlencode(buffer,LogTxt));
gives the error : invalid conversion from 'char*' to 'unsigned char*'
Should I just remove all the 'unsigned' keywords ?
system
April 2, 2012, 5:58pm
14
That's what Paul suggested - it'll work. You'll also need to add
#include <string.h>
to your headers to get a prototype for strchr().
DaveO
April 2, 2012, 6:08pm
15
couldn't add :
#include <string.h>
as it doesn't exist in my libraries.
I ran the code without it and working well, except for a few odd characters appearing :
2012-04-02---20:01:32 Setup Completed - System OperationalÝ
2012-04-02---20:01:34 Doors OpenN!
and the = converting to < in this line :
2012-04-02---20:01:33 EEProm < 0 (sms OFF+ Home)0state
I added the following to the variable :
char specials[] = "§_DISCOURSE_HOISTED_CODE_0_§+,/:;=?@ <>#%{}|~[]`";
system
April 2, 2012, 6:26pm
16
My bad (trying to carry on too many conversations at once) - I forgot to terminate the output string.
Let's try:
char specials[] = "§_DISCOURSE_HOISTED_CODE_0_§+,/:;=?@ <>#%{}|~[]`";
static char hex_digit(c)
{ return "01234567890ABCDEF"[c & 0x0F];
}
char *urlencode(char *dst,char *src)
{ char c,*d = dst;
while (c = *src++)
{ if (strchr(specials,c))
{ *d++ = '%';
*d++ = hex_digit(c >> 4);
c = hex_digit(c);
}
*d++ = c;
}
*d = '\0';
return dst;
}
It's strange to me that there's no string.h header file, but it'd appear not to have been needed. My ignorance knows no bounds!
Edit: Removed #include and simplified
DaveO
April 2, 2012, 9:25pm
17
Thanks Morris
Working like a dream now !!
Thank You so very much.
Lastly, I just have a question about this function, so that I can hopefully understand it properly :
static char hex_digit(char c)
{ return "01234567890ABCDEF"[c & 0x0F];
}
Is the purpose of this function to return either the character found in the string 01234567890ABCDEF, or if not found, then return the Hex of the 'char c' ?
If so, shouldn't the line 01234567890ABCDEF contain all 26 alpha letters, both upper and lower case ?
system
April 2, 2012, 9:55pm
18
It converts the binary value of the low-order four bits of its argument to a hexadecimal digit character . By convention, the digits after 9 are A, B, C, D, E. and F. The number after F, as you might guess, is 10 - decimal 16.
Nice little thread!
I'm currently having a similar problem -- but the other way around: I'm reading in strings from a POST HTTP response and have to decode the form variable's values. Unfortunately, a string value of "0,255,128" get's sent to the web server (running on the Arduino) as "0%2C255%2C128" because the comma character from the form's 'value=0,255,128' gets urlencoded to %2C.
Sooo, I have to decode HTML entities and was looking for a built-in (in some Arduino lib) function. To no avail.
The search function beamed me to this thread here.
Anybody who has a urldecode() function at hand that'll work on the Arduino?
Thanks so much!
Stefan.
Never mind!
Found something here: Google Code Archive - Long-term storage for Google Code Project Hosting.
Copy & pasted the two functions h2int() and urldecode() into my sketch and they work!