Обучавам се на Pro*C и това е програма с курсор през записи в база данни, която се компилира и изпълнява. Стига се до подкана „Въведете Guest_ID (напишете изход за прекратяване)>>“. След това дава грешка като „Грешка на сегментиране (ядрото е изхвърлено)“, ако е въведено цяло число. Ако се въведе низ, изглежда, че той отива в условния елемент непосредствено във външния for цикъл на
if(nGuest_ID==0)
{
printf("BYE\n");
exit(0);
}
и отпечатва "BYE", след което излиза. Тъй като все още се запознавам с това как променливите се декларират и подават от SQL, не бях сигурен кои декларации могат да бъдат от решаващо значение за отстраняване на неизправности тук, така че оставям кода до голяма степен непокътнат тук.
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
exec sql include sqlca;
// OK - Here we GO
void main()
{
// First, create all the variables that we will need to communicate between
// the "C" program and the database
exec sql begin declare section;
//VARCHAR sLastName[51], sFirstName[51], sHotelName[51], sCheckInDate[12], sRoom[11];
VARCHAR sLastName[51], sFirstName[51], sHotelName[51], sTransDate[11];
//int nDays, nGuest_ID, nCount;
int nGuest_ID, nQuantity, nUnitPrice, nCount, nHotelID, nItemID;
//VARCHAR sInCity[11];
VARCHAR sItemName[31], sTaxable[11];
VARCHAR sUserID[21], sPassword[21];
exec sql end declare section;
/////// begin needs work ///////
// Now define the cursor we will use to get all of the charges that the guest incurred at all hotels
exec sql declare dbGuest cursor for
Select G.Guest_ID, G.Last_Name, G.First_Name, C.Item_ID, C.Item_Name, C.Quantity, C.Unit_Price, C.Trans_Date, H.Hotel_Name, H.Hotel_ID, SI.Taxable
From Hotel H, Charge C, Stay S, Guest G, Sales_Item SI Where
C.Stay_ID=S.Stay_ID And H.Hotel_ID=S.Hotel_ID And G.Guest_ID=S.Guest_ID
And SI.Item_ID=C.Item_ID
Group By S.Guest_ID;
//////// end needs work ///////
// Set up the user-id and password to access my database
// Because we are using the local database on this server
// we don't need to use any database location or SID
strcpy(sUserID.arr,"myusername");
strcpy(sPassword.arr,"mypassword");
sUserID.len=strlen(sUserID.arr);
sPassword.len=strlen(sPassword.arr);
exec sql connect :sUserID identified by :sPassword;
// sqlca.sqlcode is a variable that is set based on the last command sent in to the database
// a value anything other than zero for what we just did (connect to the database) indicates
// a error.
if(sqlca.sqlcode !=0)
{
//printf("Sorry, cannot connect to server, pgm aborted %s\n",sqlca.sqlcode); //correction 2/5/14
printf("Sorry, cannot connect to server, pgm aborted %d\n",sqlca.sqlcode); //change to %d
exit(1);
}
//we made it here, so we were able to open the database correctly
exec sql SELECT COUNT(*) INTO :nCount FROM Guest;
printf ("There are %d Guests.\n",nCount);
for(;;){
// Read in through stdio the Guest we want to query, then set it up do we can use it
printf("Enter a Guest_ID(type exit to terminate)>>\n");
scanf("%d",nGuest_ID);
//Guest_ID.len= strlen(Guest_ID.arr);
if(nGuest_ID==0)
{
printf("BYE\n");
exit(0);
}
printf("%s %s %s %s %d\n","Charge Summary for:", sFirstName.arr, sLastName.arr, " Guest_ID:", nGuest_ID);
//printf("I do not work yet (type exit to terminate)>>\n");
// Open our cursor and begin reading records
exec sql open dbGuest;
for(;;)
{
//exec sql fetch dbGuest into :nGuest_ID, :sLastName, :sFirstName, :sHotelName, :sCheckInDate, :nDays, :sRoom;
exec sql fetch dbGuest into :nGuest_ID, :sLastName, :sFirstName, :nItemID, :sItemName, :nQuantity, :nUnitPrice, :sTransDate, :sHotelName, :nHotelID;
if(sqlca.sqlcode !=0) // If anything went wrong or we read past eof, stop the loop
{
break;
}
// Do the crazy stuff to end the C-Strings
sLastName.arr[sLastName.len] = 0;
sFirstName.arr[sFirstName.len] = 0;
sItemName.arr[sItemName.len] = 0;
sTransDate.arr[sTransDate.len] = 0;
sHotelName.arr[sHotelName.len] = 0;
// Print out the information for this guest
printf("%s %d %s %s \n", "Sales_Item: ", nItemID, " - ", sItemName.arr);
}
// close the cursor and end the program
exec sql close dbGuest ;
}
exit(0);
}
Сигурен съм, че правя някаква проста грешка, но не намерих нищо полезно при търсенето. Изпълнявам това на сървър и не получавам обратно отстраняване на грешки (това е единственият основен бъг, който не успях да разреша до този момент), така че това, което имате, е това, което имам и аз. Обикновено програмите на C ще се изпълняват в дебъгери, но това е ProC и съм някак загубен с цялото нещо с отстраняването на грешки в Oracle ProC (тъй като работи на отдалечена база данни). При този вид грешка обикновено подозирам, че паметта не се разпределя правилно, но не виждам нищо подобно тук.
Прегледах тези, но не помогнаха:
Грешка при сегментиране (изхвърлено ядро) грешка по време на изпълнение в C
Не толкова полезна грешка -- Грешка в сегментирането (Core Dump) в домашното задание
dbx core <ur_object_name>
може да ви покаже последния изпълнен ред! - person Maheswaran Ravisankar   schedule 20.02.2014