Newsgroup: it.comp.lang.c
Titolo: char* argv[]

Ciao NG,
Ho assegnato ad uno degli elementi di argv l'indirizzo di una nuova 
stringa (sempre allocata con malloc).
Poi ho usato free sul vecchio puntatore (precedentemente salvato) e non 
funziona.
Eppure da qualche parte ho letto:
"The startup code uses malloc to allocate storage for the _environ, 
envp, and argv variables."
#include <stdio.h>
#include <stdlib.h>
int main(int argc, char* argv[])
{
	char *pTry, *pImp;
	if(argc < 2)
		exit(1);
	pTry = malloc(7);
	sprintf(pTry, "malloc");
	printf("pTry: %p\n", pTry);
	printf("pTry: %s\n", pTry);
	printf("argv[1]: %p\n", argv[1]);
	printf("argv[1]: %s\n", argv[1]);
	pImp = argv[1];
	argv[1] = pTry;
	printf("argv[1]: %p\n", argv[1]);
	printf("argv[1]: %s\n", argv[1]);
	free(pImp);	/* Questa non va, ma perché? */
	printf("argv[1]: %p\n", argv[1]);
	printf("argv[1]: %s\n", argv[1]);
	return 0;
}
Sto cercando di fare qualcosa di impossibile?
-- 
Darkness beyond blackest pitch, deeper than the deepest
night! Lord of Darkness, shining like gold upon the Sea of
Chaos, I call upon thee, swear myself to thee! Let the fools
who stand before us be destroyed by the power you and I
possess!
GIGA SLAVE!!

 Sto cercando di fare qualcosa di impossibile?
Mi sembra proprio che non si possano modificare argc e argv.
--
 Ciao, Luca.
 Reply to 
luca....@tiscalinet.it

Sto cercando di fare qualcosa di impossibile?
Nonche' di inutile ;)
Perche' vuoi deallocare quello spazio ?

envp, and argv variables."
Perche' forse usa una sola malloc per tutte le stringhe (tiro ad
indovinare).
Saluti,
    Mardy

indovinare).
O forse perche', piu' probabile, e' il sistema che libera quelle
risorse e non il programmatore.

Una possibile soluzione credevo consistesse nell'assegnare ad argv[4] 
Brrr... brivido... ma perche' vuoi fare una cosa del genere ?
A te serve una funzione che tratti gli argomenti passati in input dal
programma.
Bene, ti basta costruire una funzione di inizializzazione del tipo :
void init_getarg( int argc, 
                  char **argv, 
                  char ***argv_rearranged )
A cui passi i parametri in input al main() e in piu' per riferimento
un puntatore a puntatori in cui riarrangi i parametri riarrangiando le
stringhe laddove risultino unite.

in un altro file.
Secondo, me, l'approccio migliore e' quello di scrivere una funzione
del genere :
/* rearranging input parameters */
/* Kalem J. Norey               */
#include <stdio.h>
#include <stdlib.h>
char *rearrange( int argc, char **argv )
{
     char *line = calloc( 1000, sizeof( char ) ) ;
     int i, k ;
     for ( i = 1, k = 0 ; i < argc ; i++ )
     {
         int j, l = strlen( argv[i] ) ;
         for ( j = 0 ; j < l ; j++ )
         {
            if ( argv[i][j] == '/' )
               line[k++] = ' ' ;
            line[k++] = argv[i][j] ;
         }
         line[k++] = ' ' ;
     }
     return line ;
}
main(int argc, char **argv)
{
    puts( rearrange( argc, argv ) ) ;
    return 0 ;
}
e ricostruire i parametri.

 succederebbe casino) ed e' giusto che non sia cosi'.
Non vorrei dire una baggianata, ma la stringa originariamente contenuta in
argv[1] il programma la dealloca automaticamente a fine esecuzione come
tutte le stringhe costanti tipo
char *mia_stringa = "stringa";
Ciao a tutti.
Gian Maria.

 argv[1] il programma la dealloca automaticamente a fine esecuzione
Esattamente.
EMG


Ma la riga dopo assegna a argv[1] l'indirizzo di pTry che e' un puntatore
allocato con malloc() e quindi l'istruzione free(argv[1]); e' corretta, tra
l'altro il programma compila e funziona mentre se scrivo free(pImp) da
errore di run time.
Gian Maria.

 Ma la riga dopo assegna a argv[1] l'indirizzo di pTry
Si, giusto. Mi era sfuggita. Comunque non so quanto sia corretto
assegnare ad argv. Meglio evitare. Tanto non ce n'è alcuna necessità.
EMG


Infatti sarebbe stato molto meglio dichiarare un proprio array di puntatori
a carattere e copiarci i valori di argv modificati, cosi' alla fine della
procedura si puo liberare con free() la memoria allocata e lasciare argv
cosi' come e'.
Gian Maria.

preferito assegnare ad uno degli elemeti di argv un indirizzo diverso.
Non che io voglia polemizzare, pero' e' proprio questo che e'
sbagliato, a mio avviso.

altro modo.
Veramente e' tutto il thread che cerco di spiegartelo, ti ho anche
scritto del codice sorgente. A mio avviso, il puntatore argv non va
toccato. Va tutto trasferito da un'altra parte e bisogna lavorare su
essa. Perche' complicarsi inutilmente la vita ?

 altro modo.
argc e argv sono in una area di memoria allocata dal loader prima che il
processo inizi la sua esecuzione. Molti sistemi operativi (quelli fatti
bene) non permettono che questa venga modificata (altri lo permettono ma poi
va tutto in crash... ;-)).
Dove si trovino i dati puntati da argv non lo so ma podarsi che siano nei
dintorni ;-)
Segui il consiglio di KalemJ.Norey...
Ps. ....ma dove è finito AL
--
________________________________
per rispondermi iliasba(at)
tin.it
bye Brain

complicarsi la vita.
Ma per favore !

 maggiore 
Suvvia, basta usare realloc().
Per esempio (scritto male e in fretta, ma rende l'idea), con riferimento
al codice postato da KJN:
...
char *line = NULL;
void writechar(char new)
{
        static int length = 1000;
        static int current = 0;
        if (line == NULL)
                line = malloc(length);
        line[current++] = new;
        if (current == length) {
                length *= 2;
                line = realloc(line, length);
        }
}
char *rearrange(int argc, char **argv)
{
        int i, j;
        for (i = 1; i < argc; i++) {
                for (j = 0; argv[i][j]; j++) {
                        if (argv[i][j] == '/')
                                writechar(' ');
                        writechar(argv[i][j]);
                }
                writechar(' ');
        }
        writechar('\0');
        return line;
}
...
Ciao ciao,
Andrea
-- 
"...Unix, MS-DOS, and Windows NT (also known as the Good, the Bad, and 
 the Ugly)."
(by Matt Welsh)

supera quel numero ci sono dei problemi.
Ci stiamo perdendo in un bicchiere d'acqua : esiste argc a cui fare
riferimento.

 Ps. ....ma dove è finito AL
Indovina... :-)
EMG