VC++: stack overflow con un array da meno di 4MB in stack?:\

Da JAVA a C# passando per PHP, SQL ed HTML
Rispondi
Avatar utente
Alessio89
Messaggi: 8095
Iscritto il: martedì 29 novembre 2011, 23:47

VC++: stack overflow con un array da meno di 4MB in stack?:\

Messaggio da Alessio89 »

Piccolo esempio con l'algoritmo di Kadane (che il massimo sottovettore): in input prendo un array letto da un semplice file testuale che può arrivare fino ad un milione di interi.

sia su linux che su windows gli int sono da 4 byte, ergo l'array è grande 4 milioni di byte, circa 3.8.. MB

Ora non ditemi che è troppo per un sistema da 16GB dove tre quarti della memoria sono liberi :|

Da quel che ricordo costanti a parte, il C++ allocava tutto quello che è statico e automatico in stack, mentre tutto quello che è allocato dinamicamente in heap.

ebbene mi da stack overflow (almeno così dice il debugger) se provo ad allocare l'array come variabile automatica, ovvero in stack.
Se lo alloco staticamente (compreso come variabile globale) o dinamicamente l'array nessun problema.

Qua allego il codice:

Codice: Seleziona tutto

/*Data una sequenza di interi A[1..N], vogliamo scegliere una sottosequenza A[I..J] tale che la somma dei propri elementi sia massima fra tutte le sottosequenze. Quale ´e la massima somma che siamo in grado di ottenere? */
#include <fstream>

int maxSubArray( int myArray[ ], const int& dimension );

int main( )
{
	int dimension = 0;
	// int myArray[ 1000000 ];


	std::ifstream inputFile("input.txt");
	inputFile >> dimension;

	int* myArray = new int[ dimension ];
	
	for( int i = 0; i < dimension; i++ )
	{
		inputFile >> myArray[ i ];
	}

	inputFile.close( );
	
	std::ofstream outputFile( "output.txt" );

	outputFile << maxSubArray( myArray, dimension );

	outputFile.close( );

	return( 0 );
}

int maxSubArray( int myArray[ ], const int& dimension )
{
	int maxValue = 0;
	int currentValue = 0;
	for( int i = 0; i < dimension; i++ )
	{
		if( ( currentValue + myArray[ i ] ) > 0 )
		{
			currentValue += myArray[ i];
		}
		else
		{
			currentValue = 0;
		}

		if( currentValue > maxValue )
		{
			maxValue = currentValue;
		}
	}
	
	return( maxValue );
}
O è Windows che ha una concezione dello stack e della heap tutto suo o sono io che ho avuto insegnamenti errati ( cosa da non scartare :asd: )

Avatar utente
Alessio89
Messaggi: 8095
Iscritto il: martedì 29 novembre 2011, 23:47

Re: VC++: stack overflow con un array da meno di 4MB in stac

Messaggio da Alessio89 »

ok a quanto èare è il modello di memoria di windows ad essere completamente diverso da quello unix : |

Avatar utente
Fottemberg
Messaggi: 19324
Iscritto il: martedì 29 novembre 2011, 22:52

Re: VC++: stack overflow con un array da meno di 4MB in stac

Messaggio da Fottemberg »

Windows non sbaglia mai, è perfetto! :asd:
PC: CoolerMaster MasterBox Q300P, AMD Ryzen 7 5800X, Thermalright Peerless Assassin 120 SE, GIGABYTE B550M AORUS ELITE, 2x32GB Patriot Viper DDR4-3600, Asus Dual RX6650XT 8GB, SSD Toshiba RC500 512GB, SSD Lexar NM790 2TB, CoolerMaster V650 Gold, Windows 11 Home
Immagine

Avatar utente
Alessio89
Messaggi: 8095
Iscritto il: martedì 29 novembre 2011, 23:47

Re: VC++: stack overflow con un array da meno di 4MB in stac

Messaggio da Alessio89 »

In realtà il C++ non prevede un modello di memoria standard, prevede semplicemente un comportamento del linguaggio: variabili automatiche in stack, statiche e globali costanti allocate all'avvio in data, e tutto il resto in heap.
Quel che windows fa è pre-allocarsi lo stack per le varie applicazioni a quanto pare, in modo da evitare problemi di collisione e overflow.
Il problema è che il compilatore non ti calcola automaticamente la dimensione massima effettiva dello stack (dato che pre-alloca una dimensione fissa o se lo fa cmq non te lo dice), in quanto già la dimensione di default dovrebbe bastare, dato che non è una buona idea allocare grandi oggetti in stack (come faceva quel programma) in quanto vanifichi l'utilità dello stack per la cpu...Su unix non mettono questi paletti e il programma (scritto con pigrizia) girava senza problemi...
In ogni caso bad programming o meno potrebbero implementare un dannato avviso di sicurezza nel compilatore... forse c'è anche se si abilitano i warning a livello massimo (ovvero demenziale) ma nessuno mai andrà ad abilitare tali impostazioni di avvisi..

Rispondi