Mail Archives: djgpp/2013/06/17/05:30:15
X-Authentication-Warning: | delorie.com: mail set sender to djgpp-bounces using -f
|
X-Received: | by 10.224.174.145 with SMTP id t17mr7618577qaz.4.1371460683820;
|
| Mon, 17 Jun 2013 02:18:03 -0700 (PDT)
|
X-Received: | by 10.50.36.41 with SMTP id n9mr394152igj.11.1371460683780; Mon,
|
| 17 Jun 2013 02:18:03 -0700 (PDT)
|
Newsgroups: | comp.os.msdos.djgpp
|
Date: | Mon, 17 Jun 2013 02:18:03 -0700 (PDT)
|
Complaints-To: | groups-abuse AT google DOT com
|
Injection-Info: | glegroupsg2000goo.googlegroups.com; posting-host=71.222.72.40; posting-account=jrLHRgkAAABPV01ZW_RN_U6Tm5UnYNUx
|
NNTP-Posting-Host: | 71.222.72.40
|
User-Agent: | G2/1.0
|
MIME-Version: | 1.0
|
Message-ID: | <36e857f0-9899-496b-9fc6-32251e109888@googlegroups.com>
|
Subject: | General Protection Fault error is intermittent
|
From: | "K.J.Williams" <lordwilliams1972 AT gmail DOT com>
|
Injection-Date: | Mon, 17 Jun 2013 09:18:03 +0000
|
Bytes: | 11134
|
Lines: | 377
|
To: | djgpp AT delorie DOT com
|
DJ-Gateway: | from newsgroup comp.os.msdos.djgpp
|
X-MIME-Autoconverted: | from quoted-printable to 8bit by delorie.com id r5H9U1ue017760
|
Reply-To: | djgpp AT delorie DOT com
|
Hi,
I have a problem with why a General Protection Fault message is not displayed all the time, for a function called string_parser in two different programs. The function called string_parser uses a string.h function called strtok(). I am trying to implement it to work right, and I know that I am not doing it correctly. But the question is why in a smaller program it compiles fine and doesn't exhibit the General Protection Fault message vs. when I implement it in a larger program it does ?
heres my source code :
/*
program name: parstext.c
author: K.J.Williams
Purpose: This is a sample of how string_parser, which uses strtok() is
used parse commands in the larger program that I am developing
called ( by acronym ) WATT.
*/
#include <stdio.h>
#include <string.h>
// original design setting:
#define PARSE_SIZE_LIMIT 81
//function prototypes:
short int string_parser(char *, char *, char, short int);//TEXT_PARSER
short int kfgets(char *);//KFGETS
short int ynreturn(void);//yes/no option
short int return_key(void);//waits for user to press ENTER
int main (void)
{
//declare char arrays and initialize garbage with '\0'
char target[PARSE_SIZE_LIMIT];//user input
char worda[PARSE_SIZE_LIMIT]; worda[0] = '\0';//command statement
char uword[PARSE_SIZE_LIMIT]; uword[0] = '\0';//argument part
//temporary variables
short int counta,countb,x,y,z;
char d;//for first character of a string
//message
printf("Compilation Date : %s @ %s PST (24hr format)\n",__DATE__,__TIME__);
printf("WATT: single text line string parsing tester\n");
printf("Enter AT Command (ATcmd) statment(s) in the syntax format of\n");
printf("[#(ATcmd): arg1 arg2 ... argN ] or [#(ATcmd): ] - for no args, and etc.\n");
//prompt user
do
{
//initialize (or reset) these variables
z = 1;
target[0] = '\0';
//prompt user
printf("\n>");
kfgets(target);//use my fgets function
d = target[0];
if(d != '#') { return 0; }// if the first character != '#' then exit...
if( (string_parser(target,worda,'#',-2)) == -1)
{
printf("text line uses incorrect syntax with adjacent \'#\' characters\n");
return 0;
}
//otherwise begin parsing....
counta = string_parser(target,worda,'#',-1);//count tokens & do nothing
string_parser(target,worda,'#',0);
printf("[%s]\n..has %d part(s) counted by \'#\'\n\n",worda,counta);
//parsing each statement and argument by '#', then ' '.
do
{
for(x = 1;x <= z;x++)
{
string_parser(target,worda,'#',x);
}
printf("part#%d : %s\n",x-1,worda);//-1 for x counter offset
countb = string_parser(worda,uword,' ',-1);
string_parser(worda,uword,' ',0);
printf("[%s]\n..has %d sub-part(s) counted by \' \'\n",uword,countb);
//if countb == 0 - then do nothing
if(countb == 1)
{
string_parser(worda,uword,' ',1);
printf("...sub-part#1 : %s\n",uword);
}
if(countb > 1)
{
for(y = 1;y <= countb;y++)
{
string_parser(worda,uword,' ',y);
printf("...sub-part#%d : %s\n",y,uword);
}
}
//pause
if(z < counta); { return_key(); }
z++;
//end of do..while loop
}while(z <= counta);
printf("\ntest again (y/n)?");
//outer do...while loop
} while((ynreturn()) == 1);
return 0;
}
//parses c strings by using single character tokens with strtok();
short int string_parser(char *userstring, char *target, char magic, short int word)
{
char subject[PARSE_SIZE_LIMIT]; subject[0] = '\0'; //initialize subject
//w1 = token with null character ; w2 = token without null character
char w1[2]; w1[0] = magic; w1[1] = '\0';
char w2[1]; w2[0] = magic;
//temp variables:
char a = 0;//copies x before the if evaluation of x - see below
char b = 0;//copies b after the if evaluation of x - see below
char c = 0;//the difference between a & b - see below
char d = 0;//d = subject[x]; - see below
char x = 0;//for loop counter
char y = 0;//counts the number of times a magic is in userstring (subject)
//only if (c > 1)
char z = 0;//same use as y, but with out the condition of if (c > 1)
//for use only when word = -2
short int length;//get the length of the string subject
char *p;//used for assigning pointer address returned by strtok()
strcpy(subject,userstring);//copy userstring to subject
length = strlen(subject);//get length of subject
//printf("\n");//temp
//printf("subject = %s\n",subject);//temp
//printf("word = %d\n",word);//temp
//printf("length = %d\n\n",length);//temp
//return the number parts in the string
if(word == -1 || word == -2)
{
//count where all the "magic" characters are
for(x = 0;x < length;x++)
{
d = subject[x];//copy the character value to d
//printf("%c : %c =",d,magic);//temp
//if the subject character = "magic" character then count it
if(d == magic)
{
if(word == -2) { z++; } //increment z regardless of where magic is found for word -2
a = x;//set a to x , to match where x is currently at.
if(x == 0) { y++; }
if(x > 0)
{
c = a - b;// c = the new count (of x) - the old count (of x)
//a magic character must have a difference between it's last
//position (if there is one) and its new position ( which is greater
//than 1 ) to be counted as magic character. Therefore, if "#" is a
//magic character and a string is, "##magic:" it would be discounted.
//However, a string such as,"# #magic:" would be counted as two
//magic characters.
//When word == -2 an additional check that the same number of
//magic characters found anywhere in subject are the same number
//of magic characters that are at least spaced apart by at least 2
//characters.
if(c > 1) { y++; } // if c > 1 then increment y
}
b = a;//set b to a , to save the previous count (of x)
//printf(" true : y = %d\n",y);//temp
}
else
{
//printf("false\n");//temp - do nothing
}
//end of for loop
}
if (word == -2) { if(z != y) { return -1; } }
return y;
}
// just copy the string - a do nothing feature
if(word == 0)
{
strcpy(target,subject);
return 0;
}
//** this is where strtok() is used **
/*
note: strtok expects the token to be a cstring without a null character
on the first use, and a token to be a cstring *with* a
null character every use after the first.
*/
//copy the first word in the string (must be done to find the next words)
if(word == 1)
{
p = strtok(subject,w2);
strcpy(target,p);
}
//copy the next word sequencially in the string as word increments by 1
if(word > 1)
{
p = strtok(NULL,w1);
strcpy(target,p);
}
return 0;
}
//generic prompt and get text from user
short int kfgets(char *target)
{
short int a;//temp. variables
char line[PARSE_SIZE_LIMIT]; line[0] = '\0'; //temp string storage
//programmer must provide a prompt for whatever information wanted
//from the user
fgets(line ,PARSE_SIZE_LIMIT, stdin);
a = strlen(line);
line[a-1] = '\0';//get rid of the newline character added by fgets
strcpy(target,line);//copy line to the target array
return 0;
}
//a simple (yes/no) branch
short int ynreturn(void)
{
short int result = 0;
char x[3];
while (fgets(x,3,stdin) != NULL && x[1] != '\n');
switch(x[0])
{
case('Y'):
case('y'):
{
result = 1;
break;
}
case('N'):
case('n'):
{
result = 0;
break;
}
//for garbage
default:
{
result = 0;
break;
}
}
return result;
}
//a ANSI C equivalent of " Press any key to continue "
short int return_key(void)
{
char x[2];
printf("\n Press Enter...\r");
while (fgets(x,2,stdin) != NULL && x[0] != '\n');
return 0;
}
(end of code)
Now, as previously stated, the program compiles fine ( I am using DJGPP for Windows 95 in MS-DOS ) and runs without a complaint.
But when I implement it in my bigger program, called WATT... I get :
Exiting due to signal SIGSEGV
General Protection Fault at eip=000093a3
eax=49420001 ebx=0001b500 ecx=00000000 edx=00000006 esi=0001b5b4 edi=0009d5c4
ebp=0009d508 esp=0009d4a0 program=C:\DJGPP\PROGRAMS\WATT.EXE
cs: sel=0187 base=8395b000 limit=000bffff
ds: sel=018f base=8395b000 limit=000bffff
es: sel=018f base=8395b000 limit=000bffff
fs: sel=0167 base=000113b0 limit=0000ffff
gs: sel=019f base=00000000 limit=0010ffff
ss: sel=018f base=8395b000 limit=000bffff
App stack: [0009d7f0..0001d7f0] Exceptn stack: [0001d74c..0001b80c]
Call frame traceback EIPs:
0x000093a3
0x000065c5
0x00005d0e
0x0000bd68
(end of message)
As you can see, from parstext.c strtok() is returning a NULL pointer which is not being checked for in either program. So I am trying to figure out why the parstext.c program is not triggering this General Protection Fault message?
Thanks.
KJW
- Raw text -