trying to stop too many enemys from spawning but im getting a stackoverfull exeption every time the counter hits 0

not sure what I am doing wrong the code looks fine too me, then again I am new too this well anyways I am making a top down shooter game using c# for my code, I have 1 enemy spawning every 30 frames but eventually it gets really laggey if you don’t kill enough, so I tried making a max enemy variable but once the enemy counter runs out i get a stack overflow exception I cant figure out what is wrong , here is my code,
if you could help me figure out whats wrong I would be very grateful.

public float spawntime = 30f;
public float maxenemy = 5;
public GameObject Enemy;
public Vector3 spawnValues;

void Update ()
{
	if (spawntime <= 0) 
		{
		SpawnWaves ();
		spawntime = spawntime + 30;
		}
	else if (spawntime > 0)
	{
		spawntime = spawntime - 1;
	}
}

void SpawnWaves ()
{
	if (maxenemy <= 0) {
					Update ();
}
	else if (maxenemy > 0) 
	{
	maxenemy = maxenemy - 1;
	Vector3 spawnPosition = new Vector3 (Random.Range (-spawnValues.x, spawnValues.x), spawnValues.y, spawnValues.z);
	Quaternion spawnRotation = Quaternion.identity;
	Instantiate (Enemy, spawnPosition, spawnRotation);
	}
}

There is a brilliant explaination written by @jbarba_ballytech on I’m getting StackOverFlowException for stack overflow which I would suggest you to read first.

The reason in your code is that you are calling Update() in your SpawnWaves(). Already Update is run each frame so you don’t need to call it explicitly unless and until required. You might want to restructure your code to get the effect you want.

99% of the time stack overflow occurs because of a reccursive calling loop. In your case yuou call Update, which calls SpawnWaves, which calls Update, which calls SpawnWaves, which calls Update, which calls SpawnWaves, which calls Update, which calls SpawnWaves, which calls Update, which calls SpawnWaves, which calls Update, which calls SpawnWaves…

Get the picture? This carries on until such time as your stack memory is full and the computer crashes out. As previously mentioned its not a good idea to call update. If you simply want your function to abort then call return instead.

Also worth noting that your code is not frame rate independent. Because I’m feeling generous this morning here is some code to try. As written this will spawn 5 enemies every 30 seconds.

public float spawntime = 30f;
public float maxenemy = 5;
public GameObject Enemy;
public Vector3 spawnValues;

void Update ()
{
    if (spawntime <= 0) 
        {
        SpawnWaves ();
        spawntime = spawntime + 30;
        }
    else if (spawntime > 0)
    {
        // Using Time.deltaTime makes the game framerate independent
        spawntime = spawntime - Time.deltaTime;
    }
}
 
void SpawnWaves ()
{
    if (maxenemy <= 0) {
        // The return statement simply exits SpawnWaves without doing anything
        return;
    }
    // This loop simply runs maxenemy times
    for (int i = 0; i < maxenemy; i++) 
    {
        Vector3 spawnPosition = new Vector3 (Random.Range (-spawnValues.x, spawnValues.x), spawnValues.y, spawnValues.z);
        Quaternion spawnRotation = Quaternion.identity;
        Instantiate (Enemy, spawnPosition, spawnRotation);
    }
}