When I try and convert my binary string to int I am receiving a couple of mistakes that I can not figure out. First I am reading from a file and the leading zeros are not showing up when I convert and the new line is showing zero.
This code I am using from this questions: Convert binary string to hexadecimal string C
char* binaryString[100];
// convert binary string to integer
int value = (int)strtol(binaryString, NULL, 2);
//output string as int
printf("%i \n",value)
My txt file and what I am expecting as an output:
00000000
000000010001001000111010
00000000000000000000000000000001
101010111100110100110001001001000101
What I get:
0
0
70202
1
-1127017915
This line:
char* binaryString[100];
Is declaring an array of 100 char pointers (or 100 strings). You probably meant this to declare a buffer of 100 characters to be interpreted as a single string:
char binaryString[100];
char *binaryString[100];
// You are creating an array of pointers in this scenario, use char binaryString[100] instead;
int value = (int)strtol(binaryString, NULL, 2);
// 101010111100110100110001001001000101 Is a 36 bit number, int (in most implementations) is 32 bit. use long long (64 bit in visual c++) as type and strtoll as function instead.
printf("%i \n",value)
Must be printf("%lld \n", value).
In summary:
#include "stdio.h"
#include "stdlib.h" // required for strtoll
int main(void)
{
char str[100] = "101010111100110100110001001001000101";
long long val = 0;
val = strtoll(str, NULL, 2);
//output string as int
printf("%lld \n", val);
return 0;
}
if im understanding this correctly you want to take a binary string so ones and zeros and convert it to a Hex string so 0-F, if so the problem is with the Write not the Convert, you specified '%i' as the written value format, what you need to do for hex is specify '%x'
Change this "printf("%i \n",value)" to "printf("%x\n",value)"
Related
I am learning C in school, and I am having a little difficulty on my project.
Basically, I am writing a function that gets a string containing a positive integer. The function subtracts 1 from that integer and puts the obtained value in the string.
So , if I have this ;
char nums[] = "2462";
how do I write a function that will subtract 1 from the integer, so that the result is "2461"??
First, convert the character array into an integer.
You can use atoi (ASCII to Integer), but because it returns 0 on error there's no way to tell the difference between successfully converting "0" and an error.
Instead use strtol (STRing TO Long integer).
// end stores where parsing stopped.
char *end;
// Convert nums as a base 10 integer.
// Store where the parsing stopped in end.
long as_long = strtol(nums, &end, 10);
// If parsing failed, end will point to the start of the string.
if (nums == end) {
perror("Parsing nums failed");
}
Now you can subtract, turn the integer back into a string with sprintf, and put it in nums.
sprintf(nums, "%ld", as_long - 1);
This is not entirely safe. Consider if nums is "0". It only has 1 byte of space. If we subtract 1 then we have "-1" and we're storing 2 characters where we only have memory for 1.
For the full explanation of how to do this safely, see How to convert an int to string in C?.
Alternatively, don't store it, just print it.
printf("%ld", as_long - 1);
One way is to convert string -> int -> string.
You can do this by using atoi and sprintf.
Simple implementation (far from perfect):
#include <stdlib.h>
#include <stdio.h>
int main()
{
int a;
char b[5];
a = atoi("2462");
a--;
sprintf(b, "%d", a);
printf("%s\n", b);
return 1;
}
I converting binary to HEXA but i need output with leading zeros. I use this number in this function -> creat(outfile, hexa_num); From 011101110111 I will get 777 but i need 0777. Here is my converting function. Any suggestions ?
char bin_final[]="011101110111";
char *a = bin_final;
int hexa_num = 0;
do {
int b = *a=='1'?1:0;
hexa_num = (hexa_num<<1)|b;
a++;
} while (*a);
Easy, just use strtoul() and regular snprintf(), no need to re-invent anything.
const unsigned long number = strtoul("011101110111", NULL, 2);
char buf[16];
snprintf(buf, sizeof buf, "%04lx", number);
puts(buf);
This prints
0777
Of course if you want to always just print it you can collapse the final three lines into just:
printf("%04lx\n", number);
You can use %04d: the 0 means leading Zeros in 4 digits.
e.g.:
printf("%04d", hexanum);
If you want it in an string use sprintf instead of printf. The number (int hexa_num) itself doesn't have leading zeros but you can format it, just as you have your binary number not as a number but as a character string.
I have string like
char str[10] = "0123456789";
I need to convert it into int. I tried it with atoi but this function removes 0. I searched it in google and found the same question here. Many answers have provided solution using strtol but its not working. Following is the code I am using for strtol:
#include <stdio.h>
#include <stdlib.h>
int main()
{
char str[30] = "0123456789 This is test";
char *ptr;
int ret;
ret = strtol(str, &ptr, 10);
printf("The number is %d\n", ret);
printf("String part is %s\n", ptr);
return(0);
}
Output:
The number is 123456789
String part is This is test
What's wrong I am doing in this case. How to convert string to int without removing zero's.
You need to format your output accordingly.
%d just prints the int in decimal using the shortest string representation (no leading zeros)
%8d (for example) will print the int in decimal in a field of size 8 (leading spaces if needed)
%08d (for example) will print the int in decimal in a field of size 8 with leading zeros.
I'm using the paillier library for cryptography.
There is a function namely paillier_ciphertext_to_bytes which converts to bytes. Upon checking the paillier.h, it has the return type void*.
I would like to take the string this generates which I believe is hex, and convert it to a decimal number using strtol.
However, when I cast the output of paillier_ciphertext_to_bytes to a char*, it doesn't work as expected.
This is my code
#include<stdio.h>
#include<stdlib.h>
#include<gmp.h>
//#include<paillier.h>
#include"paillier.h"
#include <string.h>
#include<malloc.h>
int main()
{
int n=4; //degree of polynomial
int i=0;
char* str;
paillier_pubkey_t *pub_key=(paillier_pubkey_t *)malloc(sizeof(paillier_pubkey_t));
paillier_prvkey_t *prv_key=(paillier_prvkey_t *)malloc(sizeof(paillier_prvkey_t));
paillier_keygen(4,&pub_key,&prv_key,paillier_get_rand_devrandom);
for(i=0;i<n;i++)
{
unsigned int p=rand()%20;
paillier_plaintext_t *ptext = paillier_plaintext_from_ui(p);
paillier_ciphertext_t *ctext;
ctext = paillier_enc(0, pub_key, ptext, paillier_get_rand_devrandom);
str = (char*)paillier_ciphertext_to_bytes(n,ctext);
printf("str==[%s]\n",str);
printf("number_str==[%d]\n",(int)strtol(str,NULL,16));
}
return 0;
}
This is the output I get
str==[]
number_str==[0]
str==[]
number_str==[0]
str==[]
number_str==[0]
str==[]
number_str==[0]
This is the paillier.h library code, where I looked up the signature of paillier_ciphertext_to_bytes
Side note,
I only want to convert the encryption to a number. Actually there is no reason for me to believe that paillier_ciphertext_to_bytes can be cast to a char*. So, I've also tried converting it to an int* and then print out it's value as follows
int* myintp;
myintp = (int*)paillier_ciphertext_to_bytes(n,ctext);
printf("number==[%d]\n",*myintp);
This always give me an integer number, but I'm not sure if this is correct(the decimal representation of the encrypted string)
EDIT :
As per Felix's comment, I've tried this
#include<stdio.h>
#include<stdlib.h>
#include<gmp.h>
//#include<paillier.h>
#include"paillier.h"
#include <string.h>
#include<malloc.h>
int main()
{
int n=4; //degree of polynomial
int i=0;
void* myvoid;
FILE* fp;
fp = fopen("file.txt","a");
paillier_pubkey_t *pub_key=(paillier_pubkey_t *)malloc(sizeof(paillier_pubkey_t));
paillier_prvkey_t *prv_key=(paillier_prvkey_t *)malloc(sizeof(paillier_prvkey_t));
paillier_keygen(4,&pub_key,&prv_key,paillier_get_rand_devrandom);
for(i=0;i<n;i++)
{
unsigned int p=rand()%20;
paillier_plaintext_t *ptext = paillier_plaintext_from_ui(p);
paillier_ciphertext_t *ctext;
ctext = paillier_enc(0, pub_key, ptext, paillier_get_rand_devrandom);
myvoid=paillier_ciphertext_to_bytes(PAILLIER_BITS_TO_BYTES(pub_key->bits)*2, ctext);
fwrite(myvoid, 1, PAILLIER_BITS_TO_BYTES(pub_key->bits)*2, fp);
printf("as int : %d\n",*(int*)myvoid);
printf("as str : %d\n",(int)strtol((char*)myvoid,NULL,16));
}
fclose(fp);
return 0;
}
But I get unprintable characters in my output file when I try to print myvoid, and when I cast to integer and string, I get this output
as int : 31136768
as str : 0
as int : 493106432
as str : 0
as int : 493111552
as str : 0
as int : 493092864
as str : 0
Without knowing the library in question, it's pretty clear from the name of the function what it does: It gives you the actual encrypted bytes contained in some library-specific container type. Of course you can just take it as char * (there's no need to cast and you shouldn't, but that's another question).
Typically encrypted data contains any possible byte value, which includes 0 as well as non-printable characters and so on. So, having a char * pointer to it doesn't make it a C string. What you would do now is encode it in some ascii encoding, often base64 is used. This would give you a string representation suitable for writing to a file or sending in an email.
About the part of interpreting it as an int: This is a very bad idea. As encrypted data can contain any possible byte values, it really should only be treated as this: bytes. With int you could have for example two different representations of 0, so you'd lose information. And that's just one example of what could go wrong.
char * or void * is the correct type for a sequence of arbitrary bytes. Of course, to do anything useful with it, you need to know how many bytes there are in the encrypted form. Look in your library's documentation for how to know.
I have the following piece of code compiling under gcc:
int parseMsg(const char *msg_to_parse, unsigned long *exp_input, unsigned long *sysTicks )
{
int l_msg_size = strlen(msg_to_parse);
if(l_msg_size <10)
return -1;
char l_exp_input_arr[10];
char l_sys_ticks_arr[10];
memcpy(l_sys_ticks_arr,msg_to_parse+12,10);
memcpy(l_exp_input_arr,msg_to_parse,10);
//l_msg_size = strlen(msg_to_parse);
*sysTicks = strtoul(l_sys_ticks_arr,NULL,10);
*exp_input = strtoul(l_exp_input_arr,NULL,10);
return 0;
}
And I'm trying to test it in the following manner:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int parseMsg(const char *msg_to_parse, unsigned long *exp_input, unsigned long *sysTicks );
int main(void) {
char msg[] = "1234567890 59876543213";
unsigned long along1, along2;
along1 =0;
along2=0;
parseMsg(msg,&along1, &along2 );
printf("result of parsing: \n \t Along 1 is %lu \n \t Along 2 is %lu \n",along1, along2);
return 0;
}
But, I'm getting the following result:
result of parsing:
Along 1 is 1234567890
Along 2 is 4294967295
Why is the second unsigned long wrong?
Thanks
The second integer you provide is too big to be represented in memory on your architecture. So, according to its API, strtoul is just returning you ULONG_MAX (=4294967295 on your architecture), along with setting errno to ERANGE
strtoul API is here : http://www.cplusplus.com/reference/clibrary/cstdlib/strtoul/
BUT it may also fail if you gave a smaller integer, because strtoul only stops parsing when it encounters a non-numerical character. Since you didn't ensure that, you cannot be sure that strtoul will not try to parse whatever is in memory just after your strings. (So assuming random, you have 10 chance out of 256 to have a conversion error)
Terminate your strings with \0, it will be ok then :
char l_exp_input_arr[11]; // +1 for \0
char l_sys_ticks_arr[11];
memcpy(l_sys_ticks_arr, msg_to_parse+12, 10);
l_sys_ticks_arr[10] = '\0';
memcpy(l_exp_input_arr, msg_to_parse, 10);
l_exp_input_arr[10] = '\0';
You need to make your two temporary char[] variables one char longer and then make the last character NULL.