This is my code:
#include <stdio.h>
#include <ctype.h>
#include <string.h>
#include <stdlib.h>
static int valid_line(char *cur_line) {
if (*cur_line == '#') {
return 0;
}
char *end = strchrnul(cur_line, '#');
while(end > cur_line && isspace(*end)) end--;
return (!(*cur_line == *end));
}
I am going through the line and am getting rid of leading and trailing white spaces and anything that occurs after the '#' (including the '#').
My compiler is saying this:
parser.c:20:2: warning: implicit declaration of function ‘strchrnul’ [-Wimplicit- function-declaration]
parser.c:20:14: warning: initialisation makes pointer from integer without a cast [enabled by default]
EVen though I have string.h above.
Could someone please explain.
strchrnul() is a GNU extension, and you can get this function included warning free via a feature test macro.
#define _GNU_SOURCE // required for strchrnul()
#include <stdio.h>
#include <ctype.h>
#include <string.h> // required for strchrnul()
#include <stdlib.h>
static int valid_line(char *cur_line) {
if (*cur_line == '#') {
return 0;
}
char *end = strchrnul(cur_line, '#');
while(end > cur_line && isspace(*end)) end--;
return (!(*cur_line == *end));
}
Please note from the second linked man page, the placement of the #define is important:
NOTE: In order to be effective, a feature test macro must be defined before including any header files
If you are using gcc compiler, don't use -std=c89 or -std=c99 but rather use -std=gnu89 or -std=gnu99 as strchrnul is a GNU extension.
Related
I'm trying to use functions from mman.h in my c code. The code compiles fine with g++/clang++, but when using gcc/clang it says that memfd_create has not been declared, however the code still runs fine.
I tried compiling online with godbolt and it's the same as locally, so I doubt it's something wrong with my setup. Does anyone know why this is happening? I'm using gcc 11.3 and clang 14.
#include <stdint.h>
#include <stdio.h>
#define _GNU_SOURCE
#include <sys/mman.h>
int main()
{
int32_t fd = memfd_create("", 0);
if (fd == -1)
{
printf("Error creating fd\n");
return -1;
}
return 0;
}
Compile warning:
main.c:9:15: warning: implicit declaration of function 'memfd_create' is invalid in C99 [-Wimplicit-function-declaration]
int32_t fd = memfd_create("", 0);
_GNU_SOURCE has to be before any #include. See man feature_test_macros.
#define _GNU_SOURCE
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/mman.h>
#include <stdio.h>
#include <stdlib.h>
...
int function () {
FILE *f;
f = fopen("list.txt", "rb+");
...
int value;
if (_chsize_s(f, value) == 0) return 1;
}
For some reason, the above snippet of code, when run in MS Visual Studio, generates an error at the _chsize_s() function. The following message pops up:
Debug Assertation Failed!
Expression: (fh >= 0 && (unsigned)fh < (unsigned)_nhandle)
I have no idea what to make of this, much less how to fix it. Any help would be much appreciated.
You are ignoring the compiler's warnings or have them disabled. In order to fix the implicit declaration warning, you must include the header for _chsize_s:
#include <io.h>
This will fix the implicit declaration warning, and uncover the error, that _chsize_s is being called with the wrong type. The correct way to call it is:
#include <stdio.h>
#include <stdlib.h>
#include <io.h>
...
int function(void) {
FILE *f;
f = fopen("list.txt", "rb+");
...
int value;
if (_chsize_s(_fileno(f), value) == 0) return 1;
}
This shows how important it is not to ignore compiler warnings (with exceptions... most sane people will define _CRT_SECURE_NO_WARNINGS when writing C with MSVC).
I am trying to generate function names dynamically with preprocessor directives (add a optional prefix).
The generation works and when gcc outputs me the code after the preprocessor (gcc -E), gcc tells me that the function has the right name.
But when i use this function in code, gcc throws an error with unresolved external symbol? (Link2019 / Link1120)
I'm not 100% sure how the linker works but theoretically gcc should run the preprocessor, build all the librarys (more exactly first the prototype and after the main the definition?) so there should be no problem?
Do i have to add a special compiler option? A link?
My main:
#define _CRT_SECURE_NO_WARNINGS
#define STRING_FUNCTION_PREFIX my // Defining a prefix for my string functions
#include <stdlib.h>
#include <stdio.h>
#include <string.h> // Original string functions
#include "string.h" // My string functions
#define ARRAY_SIZE 50
#define HALLO "HALLO"
#define WELT "WELT"
int main()
{
char src1[ARRAY_SIZE], src2[ARRAY_SIZE], dst1[ARRAY_SIZE], dst2[ARRAY_SIZE];
strcpy(src1, HALLO);
strcpy(dst1, WELT);
strcpy(src2, HALLO);
strcpy(dst2, WELT);
strcat(src1, dst1);
mystrcat(src2, dst2);
return 0;
}
My string.h
#pragma once
#include <stdlib.h>
#if defined STRING_FUNCTION_PREFIX
#define FUNCTION_PASTER(ARG1,ARG2) ARG1 ## ARG2
#define FUNCTION_EVALUATER(ARG1,ARG2) FUNCTION_PASTER(ARG1, ARG2)
#define FUNCTION_NAME(FUNCTION) FUNCTION_EVALUATER(STRING_FUNCTION_PREFIX, FUNCTION)
#else
#define FUNCTION_NAME(FUNCTION) FUNCTION
#endif
/*
* \brief: Adds the string from src to the destination string
*/
void FUNCTION_NAME(strcat)(char *dst, char *src);
My string.c
#include "string.h"
void FUNCTION_NAME(strcat)(char *dst, char *src)
{
int counter = 0, offset = 0;
while (dst[offset] != '\0')
{
offset++;
}
dst[offset + counter] = src[counter];
}
Output for string.h when compiling with -E
1> #line 11 "d:\\string.h"
1>
1>
1>
1>
1> void mystrcat(char *dst, char *src);
Thanks for your Help!
The STRING_FUNCTION_PREFIX directive is defined in main.c, but not in string.c. So when string.c is compiled, the substitution does not occur. If you compile string.c with gcc -E, you'll see the effect of this.
You need to put #define STRING_FUNCTION_PREFIX my at the top of string.h instead of in main.c. That way, any .c file that needs it has it defined and it's consistent in all places.
You appear to be attempting to create an emulation of templates in C. If that is the case, you should treat the contents of string.c as a header file that needs to be included by someone that knows what value STRING_FUNCTION_PREFIX should be. If the string.c contents are a header file, rename it to make that clear, for instance, string_template.h.
Then, you can have a file mystring.c implemented as:
#define STRING_FUNCTION_PREFIX my
#include "string_template.h"
So whenever I try to run my Makefile on my server, it always gives me the error is "Memory.c: 9 error: expected ')' before '*' token. But when I try to run it on my own computer, it works just fine. I've been trying to figure out what is wrong but can't seem to find it.
I've attached the 3 files that are used in this part of my program. Memory.c, Memory.h and ProcessInput.h.
This is Memory.c
/* Initializes memory */
#include <stdio.h>
#include <stdlib.h>
#include "memory.h"
void initializeMemory(memory** memArray, int memSize)
{
// Allocating space for memory array
*memArray = malloc(memSize * sizeof(memory));
if(*memArray == NULL)
{
fprintf(stderr, "Error allocating space for array of memory" );
exit(1); // exit(1) = Unsuccessful exit
}
// Initializing the contents within memory array
int i = 0;
for(i = 0; i < memSize; i ++)
{
((*memArray)[i]).occupied = false;
}
}
and this is Memory.h
// Definitions for Memory.c
#define bool int
#define true 1
#define false 0
#include "ProcessInput.h"
// Include guards to prevent redefinition of struct
#ifndef MEMORY_H
#define MEMORY_H
typedef struct memoryDetail
{
process process;
bool occupied;
} memory;
#endif
// Function declaration for memory.c
void initializeMemory(memory** memArray, int memSize);
the only thing used from ProcessInput.h is the process structure defined in ProcessInput.h
This is ProcessInput.h
// Include guards to prevent redefinition of struct
#ifndef PROCESSDETAIL_H
#define PROCESSDETAIL_H
typedef struct processDetail
{
int timeCreated;
int processID;
int memorySize;
int jobTime;
} process;
#endif
// function declarations for ProcessInput.c
void processInput(int* maxSize, int* count, process** processes, char* fileName);
I'm not too sure why it's giving me the error. I don't know where I'm supposed to be putting a missing right brace. Any advice is much appreciated!
edit: As informed, these are the following questions that I looked at but to not avail.
error: expected ‘)’ before ‘*’ token
Multiple of same error while compiling "error: expected ')' before '*' token
http://www.dreamincode.net/forums/topic/288956-error-expected-before-token/
thanks everyone for the help!
#include "memory.h" is different to #include "Memory.h" (i.e. C is case sensitive)
If you tried #include "myfile.h" instead of #include "MyFile.h" the error may be more obvious. In this case it just happens that the compiler finds the system memory.h.
<memory.h> is a header from C library of pre-standard era. It is quite possible that your standard library still provides it and the compiler takes that one instead of yours.
Try renaming your header file and see if it changes anything.
The following is my file named crack.c:
#include <stdio.h>
#define _XOPEN_SOURCE
#include <unistd.h>
void execute(char *alpha)
{
char *beta = crypt(alpha);
printf("%s", beta);
}
int main(int argc, string argv[]){
....
execute(argv[1]);
else{
printf("You submitted %d command line arguments. That's an issue. You need to submit exactly one.", argc);
return 1;
}
}
The following is what I type into the command line:
jharvard#appliance (~/Dropbox/hacker2): clang -o crack -lcrypt crack.c
The following is what the command line spits back out at me:
crack.c:8:19: warning: implicit declaration of function 'crypt' is
invalid in
C99 [-Wimplicit-function-declaration]
string beta = crypt(alpha);
^ crack.c:8:12: warning: incompatible integer to pointer conversion initializing
'string' (aka 'char *') with an expression of type 'int'
[-Wint-conversion]
string beta = crypt(alpha);
^ ~~~~~~~~~~~~ 2 warnings generated.
Anyone know what's going on?
I had the same problem, and I realized that changing the header
#define _XOPEN_SOURCE
#include <unistd.h>
by
#define _GNU_SOURCE
#include <crypt.h>
makes disapear the error in compilation time
The function signature of crypt is:
char * crypt (const char *key, const char *salt)
It seems that you forgot one parameter! So your line:
string beta = crypt(alpha);
Should be something like that:
string beta = crypt(alpha, salt);
Make sure you have the define and include for crypt as the very first lines at the top of your file before any other includes.
#define _XOPEN_SOURCE
#include <unistd.h>