ProgrammingThis forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.
Notices
Welcome to LinuxQuestions.org, a friendly and active Linux Community.
You are currently viewing LQ as a guest. By joining our community you will have the ability to post topics, receive our newsletter, use the advanced search, subscribe to threads and access many other special features. Registration is quick, simple and absolutely free. Join our community today!
Note that registered members see fewer ads, and ContentLink is completely disabled once you log in.
If you have any problems with the registration process or your account login, please contact us. If you need to reset your password, click here.
Having a problem logging in? Please visit this page to clear all LQ-related cookies.
Get a virtual cloud desktop with the Linux distro that you want in less than five minutes with Shells! With over 10 pre-installed distros to choose from, the worry-free installation life is here! Whether you are a digital nomad or just looking for flexibility, Shells can put your Linux machine on the device that you want to use.
Exclusive for LQ members, get up to 45% off per month. Click here for more info.
I am trying to convert a variable array of bytes to an unsigned long int. The number of bytes is passed into the function as tcpoptlen. Manually converting the first type bytes in the array works fine, but trying to convert n bytes crashes.
This worked to convert the first two bytes into a unsigned long integer.
Code:
tcpoptdata = (opt[i+2] << 8) | opt[i+3];
Code:
u_int64_t tcpoptdata;
u_int8_t bytefield;
u_int8_t count;
/* if the option exists, but data length is 2 */
if (tcpoptlen == 2)
return 1;
else
tcpoptdata = 0;
count = tcpoptlen - 2;
bytefield = 2;
while (count > 0) {
tcpoptdata |= opt[i + bytefield];
if (((tcpoptlen - bytefield) - 1) != 0)
tcpoptdata <<= (8 * ((tcpoptlen - bytefield) - 1));
count =- 1;
bytefield =+ 1;
}
return tcpoptdata;
opt is an unsigned char(edit actually it looks like an array of chars). tcpopelen defines how many bytes are storing bitwise data. I need to take each byte as a field, and contantonate them together so the bits remain the same in integer form.
tcpoptlen = 2 so its two bytes or 16-bit the value is 65000 or byte[1] = 11111101, byte[2] = 11101000. I need to convert them back into an integer = 1111110111101000
At least I think thats how it work. I thought it would be easier to start with reading the into before I started trying to write to opt[].
I'm (still) guessing you're looking for something along these lines:
Code:
/* warning: the following convert function makes many gross assumptions. */
#include <stdio.h>
unsigned long convert(const unsigned char *s, size_t sz)
{
unsigned long data = s[0];
for (size_t i = 1; i < sz; ++i)
data = (data << 8) | s[i];
return data;
}
int main()
{
unsigned char s[] = { 0x07, 0xF8, 0x94, 0x09 };
printf("%lu\n", convert(s, sizeof(s)));
return 0;
}
Last edited by carbonfiber; 09-22-2009 at 12:40 PM.
Well I am finally getting there. My test data is tcpoplen = 4, and opt[i+2] + opt[i+3] = the 16-bit binary value of 1460.
It works(meaning not crashing the system), but the data I get is 1461 not 1460 like it should be. So the problem is with my routine that converts the bytes into a single integer value.
Code:
u_int64_t tcpoptdata;
u_int8_t bytefield;
u_int8_t count;
/* if the option exists, but data length is 2 */
if (tcpoptlen == 2)
return 1;
else
count = opt[i+1] - 2; // get option length from header,
// and ignore header fields.
bytefield = 2; // the first data byte is always at i+2.
tcpoptdata = 0; // initialize tcpoptdata.
while (count > 0) {
count--;
if ((count) != 0) {
tcpoptdata += (opt[i+bytefield] << 8 * count);
}
else {
tcpoptdata += opt[i+bytefield];
}
bytefield++;
}
tcpoptdata |= opt[i+bytefield];
return tcpoptdata;
LinuxQuestions.org is looking for people interested in writing
Editorials, Articles, Reviews, and more. If you'd like to contribute
content, let us know.