Pointer..
-
@werdas_34 sagte in Pointer..:
Nicht ich, es wurde so generiert.
Wow. Da wird was generiert. Das erklärt auch den unsinnigen Code.
Und du erwartest jetzt, dass wir rätseln, was der Generator generiert?!Wie testet man nochmal RPC in einem Programm?
-
Wow. Da wird was generiert. Das erklärt auch den unsinnigen Code.
Und du erwartest jetzt, dass wir rätseln, was der Generator generiert?!Naja, den Thread habe ich mit dem Inhalt geöffnet, wie man sich Pointer am Besten verinnerlichen kann.
Dann kam von dir "ohne Kontext keine sinnvolle Hilfe", was ich verstehen kann.
Dann poste ich den Code und erklär was Sache ist. Jede weitere Antwort fand irgendwas schlect am generierten Code.Wenn jemand mir sagen kann wie ich im ersten Beitrag die Funktion zum laufen kriege ohne einen Speicherzugriffsfehler zu erhalten. Und da ich mit Ponter immer noch nicht ganz warm bin, dachte ich frage Experten.
Edit:
Ich habe mal ein Beispiel gemacht um das alles etwas zu verstehen (auch mit erzeugten Code). Und das funktioniert tatdellos. Auch die erste Funktion(initw) in meinem Skript funktioniert tadellos. Also am Generator liegts nicht. Er kann ineffizient sein, aber das ist mir ziemlich egal, da ich die Aufgabe löse(hoffen wirs mal), dem Prof die schicke und dann in nem halben Jahr ohne weitere Nutzung lösche. Also der Code vom Generator funktioniert.
-
@werdas_34 sagte in Pointer..:
Und das funktioniert tatdellos.
Das kannst du als Anfänger nicht beurteilen - glaube mir, den Satz habe ich hier schon hundertmal gesagt, und er ist unbestritten, denn nur weil du keinen Fehler erhältst und das Programm mit deinen Spieldaten die von dir erwarteten Ergebnisse bringt, ist das Programm noch lange nicht korrekt.
Deinen Fehler kann man nicht nachvollziehen, solange man den Aufrufkontext deine dynamischen Funktionsargumente nicht kennt, dazu gibt es u.a. Debugger.
Du greifst auf undefinierten Speicher zu, also entweder ist dein definierter (unsinnig als globales Array definiert) Speicher zu klein oder dein Index zu groß.
-
Ich starte Server und Client.
Client fragt mich nach einer Eingabe:
I
Client gibt aus Database initialized to empty.
Serverseitig wird ausgegeben: Client called initw
Ich gebe beim Client ein: i ash
Server gibt ash aus wenn printf auskommentiert ist und dann Speicherzugriffsfehler.Es kann icht daran liegen das das Wort zu groß ist oder ähnliches.
Hier mal die rdbase.h, wo weitere Sachen definiert sind:
#ifndef _RDBASE_H_RPCGEN #define _RDBASE_H_RPCGEN #include <rpc/rpc.h> #ifdef __cplusplus extern "C" { #endif #define DBASESIZE 100 #define MAXWORD 50 #define MAXRESULT 10 #define MAXSUCHERG 100 struct upd { char *upd_old; char *upd_new; }; typedef struct upd upd; struct oneword { char *word; }; typedef struct oneword oneword; struct manywords { struct { u_int words_len; oneword *words_val; } words; }; typedef struct manywords manywords; struct twoargs { char *firstarg; char *secondarg; }; typedef struct twoargs twoargs; #define RDBASEPROG 0x30090949 #define RDBASEVERS 1 #if defined(__STDC__) || defined(__cplusplus) #define INITW 1 extern int * initw_1(void *, CLIENT *); extern int * initw_1_svc(void *, struct svc_req *); #define INSERTW 2 extern int * insertw_1(char **, CLIENT *); extern int * insertw_1_svc(char **, struct svc_req *); #define DELETEW 3 extern int * deletew_1(char **, CLIENT *); extern int * deletew_1_svc(char **, struct svc_req *); #define LOOKUPW 4 extern int * lookupw_1(char **, CLIENT *); extern int * lookupw_1_svc(char **, struct svc_req *); #define UPDATEW 5 extern int * updatew_1(upd *, CLIENT *); extern int * updatew_1_svc(upd *, struct svc_req *); #define COUNTW 6 extern int * countw_1(void *, CLIENT *); extern int * countw_1_svc(void *, struct svc_req *); #define SELECTW 7 extern char ** selectw_1(void *, CLIENT *); extern char ** selectw_1_svc(void *, struct svc_req *); #define SELECTBETWEENW 8 extern manywords * selectbetweenw_1(twoargs *, CLIENT *); extern manywords * selectbetweenw_1_svc(twoargs *, struct svc_req *); extern int rdbaseprog_1_freeresult (SVCXPRT *, xdrproc_t, caddr_t); #else /* K&R C */ #define INITW 1 extern int * initw_1(); extern int * initw_1_svc(); #define INSERTW 2 extern int * insertw_1(); extern int * insertw_1_svc(); #define DELETEW 3 extern int * deletew_1(); extern int * deletew_1_svc(); #define LOOKUPW 4 extern int * lookupw_1(); extern int * lookupw_1_svc(); #define UPDATEW 5 extern int * updatew_1(); extern int * updatew_1_svc(); #define COUNTW 6 extern int * countw_1(); extern int * countw_1_svc(); #define SELECTW 7 extern char ** selectw_1(); extern char ** selectw_1_svc(); #define SELECTBETWEENW 8 extern manywords * selectbetweenw_1(); extern manywords * selectbetweenw_1_svc(); extern int rdbaseprog_1_freeresult (); #endif /* K&R C */ /* the xdr functions */ #if defined(__STDC__) || defined(__cplusplus) extern bool_t xdr_upd (XDR *, upd*); extern bool_t xdr_oneword (XDR *, oneword*); extern bool_t xdr_manywords (XDR *, manywords*); extern bool_t xdr_twoargs (XDR *, twoargs*); #else /* K&R C */ extern bool_t xdr_upd (); extern bool_t xdr_oneword (); extern bool_t xdr_manywords (); extern bool_t xdr_twoargs (); #endif /* K&R C */ #ifdef __cplusplus } #endif #endif /* !_RDBASE_H_RPCGEN */
dict wird mit [100] [51] initialisiert.
In der Funktion wird dict[0] mit argp überschrieben, da nwords anfangs 0 ist. Da durch den printf bekannt ist das argp den richtigen Wert hat und dict[0] ist ja definiert.Ich sehe jetzt nicht wo der Speicher zu klein bzw der Index zu groß sind. Kannst du das erläutern?
-
Deine Ausgabe ist fehlerhaft:
for(int k = 0; i<nwords; k++){ for(int l = 0; i<MAXWORD; l++){ printf("%s\n", dict[k][l]); } }
Du gibst einzelne Zeichen als String aus (denn
dict
ist wohl alschar
-Array deklariert und nicht alschar*
-Array, denn sonst würde der Code darüber [strcmp, strcpy
] keinen Sinn machen).
Ändere es also zufor(int k = 0; i<nwords; k++){ printf("%s\n", dict[k]); }
-
Deine Ausgabe ist fehlerhaft:
Vielen Dank. Das ist nur ein Versuch gewesen die Datenbank auszulesen, ob die Werte richtig verwendet werden.
Ich habe vergessen das auszukommentieren. Vielen Dank für die Korrektur.
Dennoch löst es das Problem leider nicht.
-
@werdas_34
Hi ich gehe immer noch davon aus, dass dein strcpy dein Problem ist.
Ich denke an dieser Stelle wird dein Speicher korrumpiert.Warum ich danke, habe da so ein Gefühl!
-
-
Gern geschehen danke denke alles das gleiche
-
Hi ich gehe immer noch davon aus, dass dein strcpy dein Problem ist.
Ich denke an dieser Stelle wird dein Speicher korrumpiert.Ich wollte wissen ob der Fehler danach kommt, oder vor dem strcpy. Also printf vor und nach der Funktion reingesetzt.
Gemerkt er gibt beides aus. Dann wieder die offensichtlich unsinnigen Pointer beim Rückgabewert hinzugefügt und es funktioniert. Ich verstehe zwar nicht ganz was ich jetzt groß anders hatte am Anfang. Aber ok.Hier mal die funktionierende Funktion(Aufruf usw ist alles gleich geblieben):
int * insertw_1_svc(char **argp, struct svc_req *rqstp) { static int result; printf("%s\n", *argp); int i; for (i=0; i<nwords; i++) if (strcmp (*argp, dict[i]) == 0) return 0; printf("Test 1\n"); strcpy(dict[nwords], *argp); printf("Test 2\n"); printf("%s\n", dict[nwords]); nwords++; result = nwords; return &result; }
-
Da du den Aufrufkontext verheimlichst, kann dir keiner helfen - was soll die Funktion überhaupt machen?
-
@werdas_34 sagte in Pointer..:
Und wieder merke ich das ich Pointer noch nicht ganz verinnerlicht habe.
Ich verstehe zwar nicht ganz was ich jetzt groß anders hatte am Anfang. Aber ok.
Und was hat das Gefrickel dir nun gebracht? Nichts.
Du hast immer noch keine Ahnung von Pointern und weißt nicht, warum dein Programm abstürzt.
Da bist du auch nicht besser als die Leute, die nach Lektüre der Pfuscher-JW Online-Sinnfreiartikeln hier aufschlagen und behaupten, sie hätten Pointer verstanden und nur noch eine kleine Frage hätten.
-
Allen frohe Ostern und bleibt gesund.
@werdas_34 sagte in Pointer..:
Hier mal die funktionierende Funktion(Aufruf usw ist alles gleich geblieben):
int * insertw_1_svc(char **argp, struct svc_req *rqstp) { static int result; printf("%s\n", *argp); int i; for (i=0; i<nwords; i++) if (strcmp (*argp, dict[i]) == 0) return 0; printf("Test 1\n"); strcpy(dict[nwords], *argp); printf("Test 2\n"); printf("%s\n", dict[nwords]); nwords++; result = nwords; return &result; }
Ein paar Fragen an Dich, da dieser Code so nicht kompiliert.
- Was sind nwords und dict? Es müssen globale Variable sein. Weshalb sind sie global definiert?
- Der Klassiker in C, weshalb wird
int
als Typ für eine Zählvariable gewählt für etwas, was dynamisch alloziert wurde?int
s können insbesondere auf 64Bit Plattformen nicht den kompletten Wertebereich von dynamisch allozierten Feldern abdecken. Es gibt dafürsize_t
undssize_t
. - Was für einen Grund hat es den Rückgabewert als lokale statische Variable zu deklarieren und dann per Zeiger zurückzugeben?
- Weshalb wird argp als ** übergeben? Was für einen Zweck erfüllt das?
-
@werdas_34
Füge mal bitte folgendes ein:int * insertw_1_svc(char **argp, struct svc_req *rqstp) { static int result; printf("%s\n", *argp); int i; for (i=0; i<nwords; i++) if (strcmp (*argp, dict[i]) == 0) return 0; printf("Length of argp:%d \n",strlen(*argp)); printf("Space in dict on position nwords:%d",sizeof(dict[nwords])); strcpy(dict[nwords], *argp); printf("Test 2\n"); printf("%s\n", dict[nwords]); nwords++; result = nwords; return &result; }
und verrate uns mal bitte die zwei Zahlen die herraus kommen