While compiling a makefile on ubuntu 12.04 LTS (64-bit) encountered with these error:
fifo.c: In function ‘OpenPipe’:
fifo.c:28:3: warning: format ‘%s’ expects argument of type ‘char *’, but argument 3 has type ‘int’ [-Wformat]
fifo.c:31:16: warning: cast to pointer from integer of different size [-Wint-to-pointer-cast]
fifo.c:33:17: warning: cast to pointer from integer of different size [-Wint-to-pointer-cast]
fifo.c:35:13: warning: cast to pointer from integer of different size [-Wint-to-pointer-cast]
fifo.c:43:16: warning: cast to pointer from integer of different size [-Wint-to-pointer-cast]
fifo.c:45:20: warning: cast to pointer from integer of different size [-Wint-to-pointer-cast]
fifo.c: In function ‘ClosePipe’:
fifo.c:132:11: warning: cast to pointer from integer of different size [-Wint-to-pointer-cast]
Here is the fifo.c :
#include "fifo.h"
#include "out_pipe.h"
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include "stdio.h"
#include <string.h>
#include "typedefs.h"
#include <sys/time.h>
#include <unistd.h>
#include "gps_sc_def.h" /* must be first */
#include "clnt_buf_def.h"
#include "s_filter.h"
//create and open pipe. If pipe exists or can not open, return -1, else 0
extern char PIPE;
extern eve_buf1 evebuf1;
extern eve_buf2 evebuf2;
extern eve_buf3 evebuf3;
short int PIPE_COUNTER=0, PIPE_PRESC_FACTOR=1;
int OpenPipe()
{
char text[64], text1[64];
**28: fprintf(stderr, "Start open Pipe: %s \n",fifo1);**
sprintf(text,"Can't create fifo ");
**31 : strcat(text, (char *)fifo0);**
sprintf(text1,"Can't create fifo ");
**33: strcat(text1, (char *)fifo1);**
**35: if((mknod((char *)fifo1, S_IFIFO | PERMS,0) < 0)&&(errno != EEXIST))**
{
perror(text1);
return -1;
}
sprintf(text1,"Can't open write fifo ");
**43 :strcat(text1,(char *) fifo1);**
**45 :if((Write = open((char *)fifo1, O_WRONLY)) == -1)**
{
perror(text1);
return -1;
}
fprintf(stderr, "Pipe opened\n");
return 0;
}
//write to pipe. if everything is OK return 0, else -1
long write2pipe(void)
{
ssize_t size2wr=0, sizeofeve=sizeof(evebuf1.nev)+sizeof(evebuf1.sec)+
sizeof(evebuf1.nsec)+sizeof(evebuf1.ireg)+sizeof(evebuf1.nsca)+
sizeof(evebuf1.nadc)+sizeof(evebuf1.ntdc)+sizeof(evebuf1.npcs);
short i,j, *p2short;
long buf[512], *p2long;
// if ((PIPE_COUNTER % PIPE_PRESC_FACTOR) != 0) return 0;
memcpy(buf,&evebuf1.nev, sizeofeve);
size2wr += sizeofeve;
/* fprintf(stderr,"sizeofeve %d\n", sizeofeve);
fprintf(stderr,"nsca %d\n", evebuf1.nsca);
fprintf(stderr,"nadc %d\n", evebuf1.nadc);
fprintf(stderr,"ntdc %d\n", evebuf1.ntdc);
fprintf(stderr,"npcs %d\n", evebuf1.npcs);
fprintf(stderr,"n_event %d\n", evebuf2.n_event); */
p2long = buf+sizeofeve/4;
p2short =(short*)(buf)+sizeofeve/2;
if(evebuf1.nsca != 0)
{
for(i=0;i<evebuf1.nsca;i++)
{
p2long[i] = evebuf3.sca[i];
//if(i<3)fprintf(stderr,"sca \t\t %d %x\n", i, evebuf3.sca[i]);
}
size2wr += 4*evebuf1.nsca;
if(write(Write,&buf, size2wr) != size2wr)
perror("wrong size\n");
return 0;
}
else
{
for(i=0;i<evebuf1.nadc;i++)
{
p2short[i] = evebuf3.adc[i];
//fprintf(stderr,"adc \t\t %x\n", evebuf3.adc[i]);
}
size2wr += 2*evebuf1.nadc;
p2short += evebuf1.nadc;
for(i=0;i<evebuf1.ntdc;i++)
{
p2short[i] = evebuf3.tdc[i];
//fprintf(stderr,"tdc \t\t %x\n", evebuf3.tdc[i]);
}
size2wr += 2*evebuf1.ntdc;
p2short += evebuf1.ntdc;
for(i=0;i<evebuf1.npcs;i++)
{
p2short[i] = evebuf3.pcos[i];
//fprintf(stderr,"\t\t %x\n", evebuf3.pcos[i]);
}
size2wr += 2*evebuf1.npcs;
if(size2wr)
if(write(Write,&buf, size2wr) != size2wr)
perror("wrong size\n");
return 0;
}
}
//close and delete pipe. 0 --- OK, -1 crash
int ClosePipe(){
close(Write);
fclose(Read);
if(unlink((char *)fifo1)<0){
perror("Can't unlink fifo");
return -1;
}
return 0;
}
By the way, I added following lines to the .profile:
export fifo0=/home/bayat/fifo0
export fifo1=/home/bayat/fifo1
please help me to solve them.
Thanks in advance.
I expect if you look (probably in fifo.h) you will find that fifo0 and fifo1 are defined as int when your program clearly expects them to be a char * or char[]. Probably what you need is something like this instead:
char fifo0[] = "/home/bayat/fifo0";
char fifo1[] = "/home/bayat/fifo1";
I do not think your .profile file has any effect whatsoever here.
Related
I'm trying to write C code to parse a config file using libconfig
The config file contains a simple element and a group. A group is composed of multiple settings, each has a unique name. ref
Config file :
host_name = "HOST";
device_settings:
{
rcu1:
{
product_id = 0x0001;
vendor_id = 0x0217;
},
rcu2:
{
product_id = 0x0001;
vendor_id = 0x0218;
}
}
I want to parse all RCUs data and store it in a data structre (the storing part is not a problem for now).
So I'm using the simple steps of :
Store the group in a config_setting_t * called section.
get length of section in a varaible called len
Iterrate len time to read RCUs data.
The problem is when i want to read RCU data i get a seg fault.
Code :
#include <libconfig.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
int main()
{
config_t cfg;
config_setting_t *root;
config_setting_t *section;
config_setting_t *elem;
int d, len;
config_init(&cfg);
if (config_read_file(&cfg,"./config.cfg") != CONFIG_TRUE) {
printf("[%s:%d] %s \n", config_error_file(&cfg),
config_error_line(&cfg), config_error_text(&cfg));
config_destroy(&cfg);
return -1;
}
if ((root = config_root_setting(&cfg)) == NULL) {
printf ("[%s:%d] %s \n", config_error_file(&cfg),
config_error_line(&cfg), config_error_text(&cfg));
config_destroy(&cfg);
return -1;
}
/* Device settings */
if ((section = config_setting_get_member(root, "device_settings")) != NULL)
{
len = config_setting_length(section);
printf("len = %d \n",len);
}
int i;
const char* device_id;
config_setting_t *device = NULL;
printf("device_settings %s a group \n",config_setting_is_group(section)?"is":"isn't");
for(i=0;i<len;i++) {
printf("iteration i = %d \n",i);
//device
if(device = config_setting_get_elem(section, i) != NULL) {
/*device id*/
if ((d = config_setting_lookup_string(device, "device_id",&device_id) != CONFIG_FALSE)) /*seg fault here*/
{
// Do stuff
}
}
}
return 0;
}
Something strange I noticed is when I compile the code i get this warning :
parse.c: In function ‘main’: parse.c:46:14: warning: assignment to
‘config_setting_t *’ {aka ‘struct config_setting_t *’} from ‘int’
makes pointer from integer without a cast [-Wint-conversion]
if(device = config_setting_get_elem(section, i) != NULL) {
GDB output :
Program received signal SIGSEGV, Segmentation fault.
0x00007ffff7da78a0 in config_setting_get_member () from
/lib/x86_64-linux-gnu/libconfig.so.9
ref to config_setting_get_elem(..)
I can not find what wrong Im doing. Everything looks correct to me.
Can someone see why the seg fault is happening?
if (device = config_setting_get_elem(section, i) != NULL)
needs to be
if ((device = config_setting_get_elem(section, i)) != NULL)
Because != has higher precedence than =.
I've tried to return a FILE pointer from some function to main().
After it, I've tried to do some fprintf on the pointer but it wasn't working.
Here is my code:
My function:
FILE *create_file(void){
FILE *regularTxt = NULL;
regularTxt = fopen("MyLogExamplekkggggggk.txt", "wt");
if (!regularTxt){
printf("error with regtxt");
getchar();
return 1;
}
char first_part_string[] = "kkkkik";
fprintf(regularTxt, "%s\n\n\n%s", "ttttg", "lklf");
return regularTxt;
}
The main function:
int main(void)
{
p_txt = create_file();
fprintf(p_txt, "%s\n\n\n%s", "gggg", "lklf");
return 0;
}
The error:
Error 92 error C4703: potentially uninitialized local pointer variable 'p_txt' used
Without all the code I can't explain the warning, but when you "return 1" from the function in the error case you didn't initialize the pointer correctly.
Change to this:
#include <stdio.h>
#include <stdlib.h>
FILE *create_file()
{
FILE *regularTxt = NULL;
regularTxt = fopen("MyLogExamplekkggggggk.txt", "wt");
if (regularTxt) {
char first_part_string[] = "kkkkik";
fprintf(regularTxt, "%s\n\n\n%s", "ttttg", "lklf");
return regularTxt;
}
return NULL; // error
}
int main(void)
{
FILE* p_txt = create_file();
if (p_txt == NULL)
{
printf("error with file");
getchar();
exit(1); // quit
}
fprintf(p_txt, "%s\n\n\n%s", "gggg", "lklf");
return 0;
}
You seem to be treating warnings as errors here. I think you should first check the returned value for NULL to silence this error:
FILE *p_txt = create_file();
if (! p_txt) {
fprintf(stderr, "[!] Failed to open the file!\n");
return 1;
} else {
fprintf(p_txt, "%s\n\n\n%s", "gggg", "lklf");
}
Also, when you're entering into if (!regularTxt), you're returning one from a function returning a pointer. Better return NULL instead.
The below works, replace 1 with NULL to remove the compiler warning shown below.
#include <stdio.h>
FILE *get(){
FILE *myfile = fopen("fio.txt", "wt");
if(1 == 2){
return 1;// this causes a warning, setting this to NULL removes the warning
}
return myfile;
}
int main(int argc, char **argv){
FILE *fp = get();
fprintf(fp, "hi there C\n");
}
fio.c:6:12: warning: incompatible integer to pointer conversion returning 'int' from a function with result type 'FILE *' (aka 'struct __sFILE *') [-Wint-conversion]
return 1;
^
1 warning generated.
the problem was becase the compailer feared when i didnt initialized the value of the pointer to NULL...thanks guys :)
I had the same problem.
Solved that adding a CAST in the function's call.
I.E.: In this example, replaced this:
p_txt = create_file();
With this:
p_txt = (FILE *) create_file();
Hope It helps!
I am new in programming with rpcgen. I created a simple rpc program which provides a remote directory listing service in Ubuntu 14.04. It uses rpcgen not only to generate stub routines, but also to generate the XDR routines.
First, the protocol file
const MAXNAMELEM = 255;
typedef string nametype<MAXNAMELEM>; /*a directory entry*/
typedef struct namenode *namelist; /*a link in the listing*/
/*a node in the directory listing*/
struct namenode {
nametype name; /*name of directory entry*/
namelist next; /*next entry*/
};
/*the result of READDIR operation*/
union readdir_res switch (int errornumber) {
case 0:
namelist list; /*no error: return directory listing*/
default:
void; /*error occurred: nothing else to return*/
};
/*the directory program definition*/
program DIRPROG {
version DIRVERS {
readdir_res READDIR(nametype) = 1;
} = 1;
} = 76;
The server:
#include <rpc/rpc.h>
#include <sys/dir.h>
#include <string.h>
#include <stdlib.h>
#include <errno.h>
#include "rdir.h"
readdir_res *readdir_1_svc(nametype *dirname, struct svc_req *req)
{
DIR *dirp = NULL;
struct direct *d = NULL;
namelist nl;
namelist *nlp = NULL;
static readdir_res res; /*must be static*/
/*open directory*/
dirp = opendir(*dirname);
if (dirp == NULL)
{
res.errornumber = errno;
return (&res);
}
/*Free previous result*/
xdr_free(xdr_readdir_res, &res);
nlp = &res.readdir_res_u.list;
while (d = readdir(dirp))
{
nl = *nlp = (namenode*)malloc(sizeof(namenode));
nl->name = strdup(d->d_name);
nlp = &nl->next;
}
*nlp = NULL;
res.errornumber = 0;
closedir(dirp);
return (&res);
}
The client:
#include <stdio.h>
#include <rpc/rpc.h>
#include "rdir.h"
int main(int argc, char *argv[])
{
CLIENT *cl;
char *server = NULL;
char *dir = NULL;
readdir_res *result = NULL;
namelist nl;
if (argc != 3)
{
fprintf(stderr, "usage: %s host directory\n", argv[0]);
exit(1);
}
/*remember what our command line arguments refer to*/
server = argv[1];
dir = argv[2];
cl = clnt_create(server, DIRPROG, DIRVERS, "tcp");
if (cl == NULL)
{
clnt_pcreateerror(server);
exit(1);
}
result = readdir_1(&dir, cl);
if (result == NULL)
{
clnt_perror(cl, server);
exit(1);
}
if (result->errornumber != 0)
{
perror(dir);
exit(1);
}
for (nl = result->readdir_res_u.list; nl!=NULL; nl=nl->next)
{
printf("%s\n", nl->name);
}
return 0;
}
Then I compile them:
rpcgen rdir.x
gcc rls.c rdir_clnt.c rdir_xdr.c -o rls
gcc rdir_svc.c dir_proc.c rdir_xdr.c -o dir_svc
When I compile with instruction:
gcc rdir_svc.c dir_proc.c rdir_xdr.c -o dir_svc
I got the following warnings:
esta#esta-U48L:~/Learning/rpcgen/dir_ls$ gcc rdir_svc.c dir_proc.c rdir_xdr.c -o dir_svc
dir_proc.c: In function ‘readdir_1_svc’:
dir_proc.c:27:2: warning: passing argument 1 of ‘xdr_free’ from incompatible pointer type [enabled by default]
xdr_free(xdr_readdir_res, &res);
^
In file included from /usr/include/rpc/rpc.h:42:0,
from dir_proc.c:1:
/usr/include/rpc/xdr.h:373:13: note: expected ‘xdrproc_t’ but argument is of type ‘bool_t (*)(struct XDR *, struct readdir_res *)’
extern void xdr_free (xdrproc_t __proc, char *__objp) __THROW;
^
dir_proc.c:27:2: warning: passing argument 2 of ‘xdr_free’ from incompatible pointer type [enabled by default]
xdr_free(xdr_readdir_res, &res);
^
In file included from /usr/include/rpc/rpc.h:42:0,
from dir_proc.c:1:
/usr/include/rpc/xdr.h:373:13: note: expected ‘char *’ but argument is of type ‘struct readdir_res *’
extern void xdr_free (xdrproc_t __proc, char *__objp) __THROW;
^
Could anybody help me out with the warning?
P.S. The program run just fine even with those warnings.
You can safely cast the arguments you pass to xdr_free:
xdr_free((xdrproc_t)xdr_readdir_res, (char *)&res);
This little project is based on this discussion about the best way to detect integer overflow before an operation is performed. What I want to do is have a program demonstrate the effectivity of utilizing the integer check. It should produce an integer overflow unchecked for some numbers, whereas it should quit before performing the operation if the check (-c) flag is used. The -m is for multiplication.
The program runs fine without the boolean part, but I need some help with the boolean part that conducts the highestOneBitPosition check. I am getting compilation errors after adding the true/false logic. I am not sure if I am calling and using the highestOneBitPosition function properly. Thanks!
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
/*boolean */
#define true 1
#define false 0
typedef int bool;
void ShowUsage ()
{
printf (
"Integer Overflow Check before performing an arithmetic.\n"
"=======================================================\n"
"Usage:\n"
"Integer Operant (-a, -s, -m, -d) Checked/Unchecked (-u, -c)\n"
"Example: ./overflowcheck 2 -a 2 -u\n"
"\n"
);
}
size_t highestOneBitPosition(uint32_t a) {
size_t bits=0;
while (a!=0) {
++bits;
a>>=1;
};
return bits;
}
int main(int argc, char *argv[]) {
if (argc != 5) {ShowUsage (); return (0);}
else if (strcmp(argv[2],"-m") == 0 && strcmp(argv[4],"-u") == 0)
{printf("%s * %s = %d -- Not checked for integer overflow.\n",argv[1],argv[3], atoi(argv[1])*atoi(argv[3]));return 0;}
/*Works fine so far */
else if (strcmp(argv[2],"-m") == 0 && strcmp(argv[4],"-c") == 0)
{
bool multiplication_is_safe(uint32_t a, uint32_t b) {
a = atoi( argv[1] );
b = atoi( argv[3] );
size_t a_bits=highestOneBitPosition(a), b_bits=highestOneBitPosition(b);
return (a_bits+b_bits<=32);}
if (multiplication_is_safe==true)
{printf("%s * %s = %d -- Checked for integer overflow.\n",argv[1],argv[3], atoi(argv[1])*atoi(argv[3]));return 0;}
if (multiplication_is_safe==false)
{printf("Operation not safe, integer overflow likely.\n");}
}
ShowUsage ();
return (0);}
compilation:
gcc integer_overflow2.c -o integer_overflow
integer_overflow2.c:40:61: error: function definition is not allowed here
bool multiplication_is_safe(uint32_t a, uint32_t b) {
^
integer_overflow2.c:45:17: error: use of undeclared identifier
'multiplication_is_safe'
if (multiplication_is_safe==true)
^
integer_overflow2.c:47:17: error: use of undeclared identifier
'multiplication_is_safe'
if (multiplication_is_safe==false)
^
[to long for a comment]
Nested functions are not supported in C.
Properly indented C sources might look like this:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
/*boolean */
#define true 1
#define false 0
typedef int bool;
void ShowUsage()
{
printf("Integer Overflow Check before performing an arithmetic.\n"
"=======================================================\n"
"Usage:\n"
"Integer Operant (-a, -s, -m, -d) Checked/Unchecked (-u, -c)\n"
"Example: ./overflowcheck 2 -a 2 -u\n"
"\n");
}
size_t highestOneBitPosition(uint32_t a)
{
size_t bits = 0;
while (a != 0)
{
++bits;
a >>= 1;
};
return bits;
}
bool multiplication_is_safe(uint32_t a, uint32_t b)
{
a = atoi(argv[1]);
b = atoi(argv[3]);
size_t a_bits = highestOneBitPosition(a), b_bits = highestOneBitPosition(b);
return (a_bits + b_bits <= 32);
}
int main(int argc, char *argv[])
{
if (argc != 5)
{
ShowUsage();
return (0);
}
else if (strcmp(argv[2], "-m") == 0 && strcmp(argv[4], "-u") == 0)
{
printf("%s * %s = %d -- Not checked for integer overflow.\n", argv[1],
argv[3], atoi(argv[1]) * atoi(argv[3]));
return 0;
}
/*Works fine so far */
else if (strcmp(argv[2], "-m") == 0 && strcmp(argv[4], "-c") == 0)
{
if (multiplication_is_safe == true)
{
printf("%s * %s = %d -- Checked for integer overflow.\n", argv[1],
argv[3], atoi(argv[1]) * atoi(argv[3]));
return 0;
}
if (multiplication_is_safe == false)
{
printf("Operation not safe, integer overflow likely.\n");
}
}
ShowUsage();
return (0);
}
There however still is a bug, which you might like to find and fix yourself. Look closely what the compiler warns you about. To enable all warnings use -Wall -Wextra -pedantic for gcc.
Check the below link:
Nested function in C
Standard C doesn't support nested functions.So you are seeing compilation errors.
Please move your function outside main() and just invoke that function from main()
The following code isn't working as expected ..
#include <stdio.h>
#include <unistd.h>
#include <string.h>
#include <stdbool.h>
struct dest
{
char filename[20], keyword[20];
bool opened;
FILE * stream;
};
void display_data(const struct dest p) {
printf("Keyword: %s, Filename: %s, Used: %s\n", p.keyword, p.filename, p.opened ? "Yes" : "No");
}
int main(int argc, char const *argv[])
{
// float lon, lat;
// char info[80];
if ((argc+1) % 2) {
fprintf(stderr, "Usage: %s file_to_read file_for_unknown type file type file ...\n", argv[0]);
return 2;
}
if (access(argv[1], F_OK) == -1) {
fprintf(stderr, "File can't be accessed: %s\n", argv[1]);
return 2;
}
const short pairs = (argc-3)/2;
struct dest data[pairs];
short times = 4;
for(short i = 4; i < argc; i += 2) {
struct dest data[i-times];
data[i-times].opened = false;
strcpy(data[i-times].keyword, argv[i-1]);
strcpy(data[i-times].filename, argv[i]);
// display_data(data[i-times]);
times += 1;
}
display_data(data[0]);
return 0;
}
That's what happens when I try to run it ..
./categorize spooky.csv other.csv UFO UFOS.csv
Keyword: ?, Filename: �#, Used: No
Which isn't that meaningful ..
I have been trying to work out the solution .. in vein ..
I don't understand where the problem is ..
Arguments are parsed as follows:
The first argument: the file the program is supposed to read from (ignored for now)
The second argument: the file the program is supposed to store at any unknown info found in the spooky.csv file (also, ignored in this implementation)
The other arguments: they are parsed as pairs, the first is the keyword, the second is the file ..
My Solution for this filtering problem was to create an array of structs, and within each struct I store the keyword, the filename and the file io stream (which i am ignoring, for now) ..
Any help would be highly appreciated ..
You have 2 struct dest data[] arrays. The inner one is masking the outer - get rid of it.
Your compiler is probably warning about this, if you have warnings turned on.