Torna indietro   Hardware Upgrade Forum > Software > Programmazione

Nioh 3: souls-like punitivo e Action RPG
Nioh 3: souls-like punitivo e Action RPG
Nioh 3 aggiorna la formula Team NINJA con aree esplorabili più grandi, due stili di combattimento intercambiabili al volo (Samurai e Ninja) e un sistema di progressione pieno di attività, basi nemiche e sfide legate al Crogiolo. La recensione entra nel dettaglio su combattimento, build, progressione e requisiti PC
Test in super anteprima di Navimow i220 LiDAR: il robot tagliaerba per tutti
Test in super anteprima di Navimow i220 LiDAR: il robot tagliaerba per tutti
La facilità di installazione e la completa automazione di tutte le fasi di utilizzo, rendono questo prodotto l'ideale per molti clienti. Ecco com'è andata la nostra prova in anteprima
Dark Perk Ergo e Sym provati tra wireless, software via browser e peso ridotto
Dark Perk Ergo e Sym provati tra wireless, software via browser e peso ridotto
be quiet! debutta nel settore mouse da gaming con Dark Perk Ergo e Dark Perk Sym: due modelli gemelli per specifiche, con polling rate di 8.000 Hz anche in wireless, sensore PixArt PAW3950 da 32.000 DPI e autonomia dichiarata fino a 110 ore. Nel test, a 8.000 Hz si arriva a circa 30 ore reali, con ricarica completa in un'ora e mezza
Tutti gli articoli Tutte le news

Vai al Forum
Rispondi
 
Strumenti
Old 10-03-2007, 15:29   #1
Matrixbob
Senior Member
 
L'Avatar di Matrixbob
 
Iscritto dal: Jul 2001
Messaggi: 9947
[C] Buffer di caratteri: inizializzarlo & funzioni per stringhe

Non so se è corretto, ma io faccio così:
Codice:
titolo_str[0]='\0';
strcpy(titolo_str, "##### TITOLO DEL ITEM #####\n");
Forse è meglio usare la strcat?!
Secondo me no, perchè se il buffer è sporco, nel concatenare può fare dei casini.

Ammesso che pulire/ripulire/inizializzare 1 buffer di caratteri si faccia come faccio io.
__________________
Aiuta la ricerca col tuo PC: >>Calcolo distribuito BOINC.Italy: unisciti anche tu<<
Più largo è il sorriso, più affilato è il coltello.
Matrixbob è offline   Rispondi citando il messaggio o parte di esso
Old 10-03-2007, 15:59   #2
xorshadow
Member
 
L'Avatar di xorshadow
 
Iscritto dal: Feb 2007
Messaggi: 38
Per inizializzare un buffer si fa così di solito:

Codice:
memset(buffer, 0, DIMENSIONE_BUFFER);
riempie TUTTO il buffer di zeri e non solo il primo carattere.

Per riempirlo è meglio che usi la versione sicura di strcpy,ovvero strncpy che ti aiuta a prevenire pericolosi buffer overflow.
xorshadow è offline   Rispondi citando il messaggio o parte di esso
Old 10-03-2007, 18:42   #3
Matrixbob
Senior Member
 
L'Avatar di Matrixbob
 
Iscritto dal: Jul 2001
Messaggi: 9947
Quote:
Originariamente inviato da xorshadow Guarda i messaggi
Per inizializzare un buffer si fa così di solito:

Codice:
memset(buffer, 0, DIMENSIONE_BUFFER);
riempie TUTTO il buffer di zeri e non solo il primo carattere.

Per riempirlo è meglio che usi la versione sicura di strcpy,ovvero strncpy che ti aiuta a prevenire pericolosi buffer overflow.
Io mi son fatto questa funzioncina:
Codice:
void pulisci_str(char *stringa, int lunghezza)
{
int i;

for (i=0; i<lunghezza; ++i) { stringa[i]='\0'; }
}
, perchè secondo me 1 vettore di caratteri va inizzializzato con il carattere nullo \0 no?!
__________________
Aiuta la ricerca col tuo PC: >>Calcolo distribuito BOINC.Italy: unisciti anche tu<<
Più largo è il sorriso, più affilato è il coltello.
Matrixbob è offline   Rispondi citando il messaggio o parte di esso
Old 10-03-2007, 19:57   #4
Matrixbob
Senior Member
 
L'Avatar di Matrixbob
 
Iscritto dal: Jul 2001
Messaggi: 9947
Quote:
Originariamente inviato da Antonio23 Guarda i messaggi
se inizializzi solo il primo carattere, non è detto che gli altri non siano sporchi, per cui si usa memset, che inizializza tutti i caratteri con '\0'
Quindi memset fa già quello che io ho fatto nella mia funzioncina?!
Cancello la mia funzione e uso memset?!
__________________
Aiuta la ricerca col tuo PC: >>Calcolo distribuito BOINC.Italy: unisciti anche tu<<
Più largo è il sorriso, più affilato è il coltello.
Matrixbob è offline   Rispondi citando il messaggio o parte di esso
Old 10-03-2007, 19:59   #5
Matrixbob
Senior Member
 
L'Avatar di Matrixbob
 
Iscritto dal: Jul 2001
Messaggi: 9947
Quote:
Originariamente inviato da xorshadow Guarda i messaggi
Per riempirlo è meglio che usi la versione sicura di strcpy,ovvero strncpy che ti aiuta a prevenire pericolosi buffer overflow.
Ovvero come si usa sta strncopy?!
__________________
Aiuta la ricerca col tuo PC: >>Calcolo distribuito BOINC.Italy: unisciti anche tu<<
Più largo è il sorriso, più affilato è il coltello.
Matrixbob è offline   Rispondi citando il messaggio o parte di esso
Old 10-03-2007, 23:51   #6
andbin
Senior Member
 
L'Avatar di andbin
 
Iscritto dal: Nov 2005
Città: TO
Messaggi: 5206
Quote:
Originariamente inviato da Matrixbob Guarda i messaggi
Non so se è corretto, ma io faccio così:
Codice:
titolo_str[0]='\0';
strcpy(titolo_str, "##### TITOLO DEL ITEM #####\n");
Forse è meglio usare la strcat?!
Secondo me no, perchè se il buffer è sporco, nel concatenare può fare dei casini.
Non vedo come possa fare casini. strcpy() copia tutti i caratteri della stringa sorgente, nullo compreso.

Es.
Codice:
char str[50];
strcpy (str, "Hello");
strcat (str, " World");
è più che corretto.
__________________
Andrea, SCJP 5 (91%) - SCWCD 5 (94%)
andbin è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 00:36   #7
xorshadow
Member
 
L'Avatar di xorshadow
 
Iscritto dal: Feb 2007
Messaggi: 38
Quote:
Originariamente inviato da andbin Guarda i messaggi
Non vedo come possa fare casini. strcpy() copia tutti i caratteri della stringa sorgente, nullo compreso.

Es.
Codice:
char str[50];
strcpy (str, "Hello");
strcat (str, " World");
è più che corretto.
Nel tuo esempio è impossibile che ci siano problemi, visto che stai passando al buffer una stringa costante.
Metti il caso, invece, che tu stia facendo un'applicazione di rete e che debba copiare il contenuto di una stringa ricevuta in input dall'utente.
Nel migliore delle ipotesi l'utente ingenuamente passa una stringa più lunga del tuo buffer e il programma va in crash.
Nel peggiore dei casi, invece, trovi un hacker che ti provoca un bel buffer overflow e prende il controllo della tua macchina.
Quindi è buona norma scordarsi completamente della strcpy e usare strncpy che permette di limitare il numero di caratteri copiati nel tuo buffer.
xorshadow è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 09:07   #8
DanieleC88
Senior Member
 
L'Avatar di DanieleC88
 
Iscritto dal: Jun 2002
Città: Dublin
Messaggi: 5989
Quote:
Originariamente inviato da xorshadow Guarda i messaggi
Per inizializzare un buffer si fa così di solito:

Codice:
memset(buffer, 0, DIMENSIONE_BUFFER);
riempie TUTTO il buffer di zeri e non solo il primo carattere.
Alternativamente, invece che malloc(), potrebbe anche usare calloc() al momento dell'allocazione, visto che azzera da sola il contenuto della memoria allocata.
__________________

C'ho certi cazzi Mafa' che manco tu che sei pratica li hai visti mai!
DanieleC88 è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 14:11   #9
Matrixbob
Senior Member
 
L'Avatar di Matrixbob
 
Iscritto dal: Jul 2001
Messaggi: 9947
Come diceva qualcuno è 1 apz che cicla con quei buffer che erano variabili globali.
Quindi ho pensato di cambiare tecnica adesso:
ho fatto che togliere i buffer di dimensioni fisse, ed adopero la seguente tenica adesso:

bla bla bla

lunghezza=strlen("");
str_tmp=(char*) calloc(lunghezza, sizeof(char));
sprintf(str_tmp, "e%d = ImageReader(\"no_input.png\",0,250,25.00).ConvertToYV12()\n", count_item);
strcat(enclosure_str, str_tmp);
free(str_tmp);

bla bla bla


Speriamo di non aver fatto 1 !!!
__________________
Aiuta la ricerca col tuo PC: >>Calcolo distribuito BOINC.Italy: unisciti anche tu<<
Più largo è il sorriso, più affilato è il coltello.

Ultima modifica di Matrixbob : 11-03-2007 alle 14:14.
Matrixbob è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 14:13   #10
Matrixbob
Senior Member
 
L'Avatar di Matrixbob
 
Iscritto dal: Jul 2001
Messaggi: 9947
Quote:
Originariamente inviato da DanieleC88 Guarda i messaggi
Alternativamente, invece che malloc(), potrebbe anche usare calloc() al momento dell'allocazione, visto che azzera da sola il contenuto della memoria allocata.
Ehm ... la malloc proprio non l'ha menzionata nessuno.

[PS]
Ma mettere tutti \0 equivale a riempire la stringa di 0?!
__________________
Aiuta la ricerca col tuo PC: >>Calcolo distribuito BOINC.Italy: unisciti anche tu<<
Più largo è il sorriso, più affilato è il coltello.

Ultima modifica di Matrixbob : 11-03-2007 alle 14:15.
Matrixbob è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 14:21   #11
DanieleC88
Senior Member
 
L'Avatar di DanieleC88
 
Iscritto dal: Jun 2002
Città: Dublin
Messaggi: 5989
Quote:
Originariamente inviato da Matrixbob Guarda i messaggi
Ehm ... la malloc proprio non l'ha menzionata nessuno.

[PS]
Ma mettere tutti \0 equivale a riempire la stringa di 0?!
Primo, dal momento che ti preoccupavi di azzerare la stringa con memset() deducevo che tale operazione non fosse stata già effettuata prima, quindi presumevo che l'allocazione fosse stata fatta con malloc(): facendola con calloc() non hai bisogno di azzerare niente.
Secondo, '\0' è una sequenza di escape, e non va a riempire ogni carattere della stringa con il carattere '0' (ASCII 49), ma con un carattere non visualizzabile che indica un carattere nullo (ASCII 0, usato appunto come terminatore di stringa dalle operazioni del C).
__________________

C'ho certi cazzi Mafa' che manco tu che sei pratica li hai visti mai!
DanieleC88 è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 14:43   #12
Matrixbob
Senior Member
 
L'Avatar di Matrixbob
 
Iscritto dal: Jul 2001
Messaggi: 9947
Quote:
Originariamente inviato da DanieleC88 Guarda i messaggi
Primo, dal momento che ti preoccupavi di azzerare la stringa con memset() deducevo che tale operazione non fosse stata già effettuata prima, quindi presumevo che l'allocazione fosse stata fatta con malloc(): facendola con calloc() non hai bisogno di azzerare niente.
La definizione di 1 VAR globale è lo stesso di una malloc?!

Quote:
Originariamente inviato da DanieleC88 Guarda i messaggi
Secondo, '\0' è una sequenza di escape, e non va a riempire ogni carattere della stringa con il carattere '0' (ASCII 49), ma con un carattere non visualizzabile che indica un carattere nullo (ASCII 0, usato appunto come terminatore di stringa dalle operazioni del C).
Ma quindi il memset come l'andavo a richiamare per avere 1 risultato equivalente alla mia funzione:
Codice:
//richiamata
pulisci_str(stringa, SIZEBUF);

//definita
void pulisci_str(char *stringa, int lunghezza)
{
int i;

for (i=0; i<lunghezza; ++i) { stringa[i]='\0'; }
}


Codice:
memset(buffer, 0, DIMENSIONE_BUFFER);
oppure
Codice:
memset(buffer, '\0', DIMENSIONE_BUFFER);
__________________
Aiuta la ricerca col tuo PC: >>Calcolo distribuito BOINC.Italy: unisciti anche tu<<
Più largo è il sorriso, più affilato è il coltello.

Ultima modifica di Matrixbob : 11-03-2007 alle 14:45.
Matrixbob è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 14:46   #13
Matrixbob
Senior Member
 
L'Avatar di Matrixbob
 
Iscritto dal: Jul 2001
Messaggi: 9947
Ma soprattutto, questa tecnica ora è corretta, funziona?!

bla bla bla

lunghezza=strlen("");
str_tmp=(char*) calloc(lunghezza, sizeof(char));
sprintf(str_tmp, "e%d = ImageReader(\"no_input.png\",0,250,25.00).ConvertToYV12()\n", count_item);
strcat(enclosure_str, str_tmp);
free(str_tmp);

bla bla bla
__________________
Aiuta la ricerca col tuo PC: >>Calcolo distribuito BOINC.Italy: unisciti anche tu<<
Più largo è il sorriso, più affilato è il coltello.
Matrixbob è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 15:50   #14
Matrixbob
Senior Member
 
L'Avatar di Matrixbob
 
Iscritto dal: Jul 2001
Messaggi: 9947
ARRIVANO I GUAI: pare che la sprintf mi scazzi le stringhe!
Pezzo del mio codice:

lunghezza=strlen("##### TITOLO DEL ITEM #####\n");
titolo_str=(char*) calloc(lunghezza, sizeof(char));
strcpy(titolo_str, "##### TITOLO DEL ITEM #####\n");
printf("titolo_str: %s\n", titolo_str);
getchar();

lunghezza=strlen("");
str_tmp=(char*) calloc(lunghezza, sizeof(char));
printf("str_tmp1: %s\n", str_tmp);
printf("canale_titolo: %s", canale_titolo);
getchar();

sprintf(str_tmp, "bottom_subs%d = Subtitle(bottom,\"\"\"%s\\n", count_item, canale_titolo);
printf("str_tmp2: %s\n", str_tmp);
getchar();

strcat(titolo_str, str_tmp);
printf("titolo_str: %s\n", titolo_str);
getchar();

free(str_tmp);



Cavolo mi sono proprio impastato!!!
Qui ho proprio bisogno di 1 vostro aiuto.
Forse le stringhe che hanno a che fare con sprintf è meglio se le lascio di dimensione fissa sovradimensionata?!
__________________
Aiuta la ricerca col tuo PC: >>Calcolo distribuito BOINC.Italy: unisciti anche tu<<
Più largo è il sorriso, più affilato è il coltello.

Ultima modifica di Matrixbob : 11-03-2007 alle 16:05.
Matrixbob è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 16:13   #15
Matrixbob
Senior Member
 
L'Avatar di Matrixbob
 
Iscritto dal: Jul 2001
Messaggi: 9947
Adesso ho fatto così, ma ho paura che scazzi nuovamente quando i %s e %d vengono sostituiti:

lunghezza=strlen("##### TITOLO DEL ITEM #####\n");
titolo_str=(char*) calloc(lunghezza, sizeof(char));
strcpy(titolo_str, "##### TITOLO DEL ITEM #####\n");

lunghezza=strlen("bottom_subs%d = Subtitle(bottom,\"\"\"%s\\n");
str_tmp=(char*) calloc(lunghezza, sizeof(char));

sprintf(str_tmp, "bottom_subs%d = Subtitle(bottom,\"\"\"%s\\n", count_item, canale_titolo);
strcat(titolo_str, str_tmp);
free(str_tmp);

... però attendo fiducioso da voi il giusto verbo!!
__________________
Aiuta la ricerca col tuo PC: >>Calcolo distribuito BOINC.Italy: unisciti anche tu<<
Più largo è il sorriso, più affilato è il coltello.

Ultima modifica di Matrixbob : 11-03-2007 alle 16:22.
Matrixbob è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 17:18   #16
xorshadow
Member
 
L'Avatar di xorshadow
 
Iscritto dal: Feb 2007
Messaggi: 38
Quote:
Originariamente inviato da Matrixbob Guarda i messaggi
Adesso ho fatto così, ma ho paura che scazzi nuovamente quando i %s e %d vengono sostituiti:

lunghezza=strlen("##### TITOLO DEL ITEM #####\n");
titolo_str=(char*) calloc(lunghezza, sizeof(char));
strcpy(titolo_str, "##### TITOLO DEL ITEM #####\n");

lunghezza=strlen("bottom_subs%d = Subtitle(bottom,\"\"\"%s\\n");
str_tmp=(char*) calloc(lunghezza, sizeof(char));

sprintf(str_tmp, "bottom_subs%d = Subtitle(bottom,\"\"\"%s\\n", count_item, canale_titolo);
strcat(titolo_str, str_tmp);
free(str_tmp);

... però attendo fiducioso da voi il giusto verbo!!
Il problema in realtà è un pò più complesso.
Tu vuoi copiare una stringa di cui non conosci a priori la lunghezza (a causa della formattazione di sprintf) . Dovresti fare così:
1) Usi snprintf e non sprintf che ti permette di limitare il caratteri copiati (guardati il manuale per sapere come funziona)
2) Algoritmo "serio" : crei un buffer di dimensioni piccole(anche 0 byte) con malloc, copi la stringa con snprintf , guardi il valore di ritorno, se questo è maggiore della dimensione del buffer vuol dire che il buffer non bastava e la stringa è stata troncata, in questo caso devi riallocare il buffer creandolo più grande (pari al valore di ritorno dell snprintf+1) e riprovi a fare la copia.

Ultima modifica di xorshadow : 11-03-2007 alle 18:45.
xorshadow è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 17:39   #17
cionci
Senior Member
 
L'Avatar di cionci
 
Iscritto dal: Apr 2000
Città: Vicino a Montecatini(Pistoia) Moto:Kawasaki Ninja ZX-9R Scudetti: 29
Messaggi: 53971
Quote:
Originariamente inviato da Matrixbob Guarda i messaggi
lunghezza=strlen("");
str_tmp=(char*) calloc(lunghezza, sizeof(char));
sprintf(str_tmp, "e%d = ImageReader(\"no_input.png\",0,250,25.00).ConvertToYV12()\n", count_item);
strcat(enclosure_str, str_tmp);
free(str_tmp);
E' errato...allochi a str_tmp un solo byte...in quanto lunghezza è pari a 1.
L'unico modo per dimensionare in modo corretto la stringa è convertire prima su un buffer temporaneo count_item.

char template[] = "e%d = ImageReader(\"no_input.png\",0,250,25.00).ConvertToYV12()\n";

str_tmp = (char *)malloc(12 * sizeof(char));
sprintf(str_tmp, "%d", count_item);
lunghezza = strlen(str_tmp) + strlen(template) - 2; //-2 perché tolgo i caratteri dovuti a "%d"

free(str_temp);
str_tmp = (char *)malloc((lunghezza + 1) * sizeof(char));
sprintf(str_tmp, template, count_item);

strcat(enclosure_str, str_tmp);
free(str_temp);

Ricordati che perà enclosure_str deve avere abbastanza spazio per contenere anche l'altra stringa..
cionci è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 20:29   #18
xorshadow
Member
 
L'Avatar di xorshadow
 
Iscritto dal: Feb 2007
Messaggi: 38
Come ho già detto prima (versione semplificata e senza error check):

Codice:
nchars = snprintf(NULL, 0, "Quello che %s devi %d formattare", arg1, arg2);
char* buff = malloc(nchars + 1);
snprintf(buff,nchars + 1,"Quello che %s devi %d formattare", arg1, arg2);
Semplice, veloce (la versione non semplificata che ti ho suggerito su può essere più veloce), riutilizzabile. Tutto qui.

Ultima modifica di xorshadow : 11-03-2007 alle 20:32.
xorshadow è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 20:41   #19
cionci
Senior Member
 
L'Avatar di cionci
 
Iscritto dal: Apr 2000
Città: Vicino a Montecatini(Pistoia) Moto:Kawasaki Ninja ZX-9R Scudetti: 29
Messaggi: 53971
Interessante questa snprintf...non la conoscevo. Ho visto che è anche nello standard C99, ottimo
cionci è offline   Rispondi citando il messaggio o parte di esso
Old 11-03-2007, 20:59   #20
Matrixbob
Senior Member
 
L'Avatar di Matrixbob
 
Iscritto dal: Jul 2001
Messaggi: 9947
Bene bene, s'imparano sempre delle belle cose.
C'è anche la matrixNbob function?!
Mi farò 1 bel stamp di questo 3D poi come promemoria.
__________________
Aiuta la ricerca col tuo PC: >>Calcolo distribuito BOINC.Italy: unisciti anche tu<<
Più largo è il sorriso, più affilato è il coltello.
Matrixbob è offline   Rispondi citando il messaggio o parte di esso
 Rispondi


Nioh 3: souls-like punitivo e Action RPG Nioh 3: souls-like punitivo e Action RPG
Test in super anteprima di Navimow i220 LiDAR: il robot tagliaerba per tutti Test in super anteprima di Navimow i220 LiDAR: i...
Dark Perk Ergo e Sym provati tra wireless, software via browser e peso ridotto Dark Perk Ergo e Sym provati tra wireless, softw...
DJI RS 5: stabilizzazione e tracking intelligente per ogni videomaker DJI RS 5: stabilizzazione e tracking intelligent...
AMD Ryzen 7 9850X3D: Zen 5, 3D V-Cache e frequenze al top per il gaming AMD Ryzen 7 9850X3D: Zen 5, 3D V-Cache e frequen...
Fire TV Omni QLED, Serie 2 e Serie 4: le...
Con l'Event Horizon Telescope si sta stu...
Milano Cortina 2026, dietro le quinte de...
IA e automazione: le armi per industrial...
SpaceX sta per rimuovere il braccio di a...
Sony a ISE 2026: display, soluzioni imme...
Sony punta sull'IA: brevettati i podcast...
Logitech G Astro A50, le cuffie gaming d...
Lenovo a ISE 2026: smart collaboration, ...
GeForce RTX 5000 SUPER cancellate e RTX ...
Substack conferma violazione: esposti da...
L'IA costa caro. Oracle punta a raccogli...
OpenAI lancia Frontier: il cervello cent...
Questo robot aspirapolvere lava sempre c...
Il PC non si avvia? ASRock invita a cont...
Chromium
GPU-Z
OCCT
LibreOffice Portable
Opera One Portable
Opera One 106
CCleaner Portable
CCleaner Standard
Cpu-Z
Driver NVIDIA GeForce 546.65 WHQL
SmartFTP
Trillian
Google Chrome Portable
Google Chrome 120
VirtualBox
Tutti gli articoli Tutte le news Tutti i download

Strumenti

Regole
Non Puoi aprire nuove discussioni
Non Puoi rispondere ai messaggi
Non Puoi allegare file
Non Puoi modificare i tuoi messaggi

Il codice vB è On
Le Faccine sono On
Il codice [IMG] è On
Il codice HTML è Off
Vai al Forum


Tutti gli orari sono GMT +1. Ora sono le: 22:01.


Powered by vBulletin® Version 3.6.4
Copyright ©2000 - 2026, Jelsoft Enterprises Ltd.
Served by www3v