0

I'm creating a game in the Blender Game Engine. And I have coded an IRC script which works fine on OS X and Linux distros. The output is similar to this:

Logging in...
LOGIN_ERROR
LOGIN_ERROR
LOGIN_ERROR
LOGIN_ERROR
LOGIN_ERROR
LOGIN_ERROR
<name> has joined.
Logged in!

And then I can call my sendmsg() function to send messages to the IRC channel.

This is the error I get when I try to run on Windows 7: stack overflow python sockets error

My python IRC code: http://pastebin.com/aG6TwTir

Ignore the "bge" references. Those variables and such are filled from the game engine.

In the game engine, I call login() once, and it spits out "LOGIN_ERROR" so I know it's trying to connect, and then it will connect, therefore not throwing an exception and ending the function.

In OS X and Linux, it runs perfectly and seemlessly in the background while the player can continue to play as it connects.

In windows 7, it throws that error.

So I guess what needs to happen is a way to wait for the script to connect to the server. Then once connected, I can send the login information and join the channel.

So how do I wait for the connection?

FYI: I have the sockets non-blocking, since the script needs to run on the same thread as the game engine, on every frame. Main() is run every frame, not the whole script. At the menu, it executes the script and calls login(). Then once in the game, it will call Main() every frame. Oh and I'm using Python 3.3.

Any help is greatly apreciated! ^_^

EDIT: How do I handle this exception? irc exception

2 Answers2

1

This code:

def login():
    ...
    try:
        ...
    except:
        ...
        login()  #  <===

recursively calls itself; given a high enough number of login failures, depending on the stack size limit (which depends on platform I guess), you'll get a stack overflow.

See also: Setting stacksize in a python script

Although I would always just avoid recursion and use looping instead, unless I know in advance that the recursion depth will never be more than ~100:

while True:
    try:
        do_login()
    except:  # NOTE: USE A SPECIFIC EXCEPTION CLASS HERE, BTW
        continue
    else:
        break
Community
  • 1
  • 1
Erik Kaplun
  • 37,128
  • 15
  • 99
  • 111
  • Oh ohkay I understand that issue now! Thanks ^_^ Though the only problem in doing a loop, is that it will block the thread that the game engine it running on until the loop ends. – user3001105 Mar 06 '14 at 20:13
  • @user3001105: recursion has the exact same semantics with regards to threading/blocking as looping; if you want non-blocking behavior, you need to either use a separate thread, or use something like gevent. – Erik Kaplun Mar 06 '14 at 20:22
  • Ohkay so I have to use looping... or threading. But in both cases I need to have a way of knowing when the connection has been made (or failed) so that I can break the loop/thread to continue gameplay. – user3001105 Mar 06 '14 at 20:40
  • How do I check for the exception in the picture? That error does not come up in OSX or Linux. So if I could check for that exception, then it will work as I could handle how long it will block. (the picture is edited into the original question) – user3001105 Mar 06 '14 at 20:56
  • hmm, do you have any prior experience with non-blocking sockets or non-blocking IO in general? because by the things you're saying (e.g. "so I have to use looping or threading") I'd suggest trying to tackle a simpler problem first... – Erik Kaplun Mar 06 '14 at 21:07
  • Yes I have, but I'm still learning haha. I meant that I am "stuck" using a loop (which will freeze gameplay until finished) or threading (which hasn't been tested in the game engine yet). If that makes sense... I found OSError: http://docs.python.org/dev/library/exceptions.html#OSError I just don't know how to implement it into the exception clause. Thanks for all your help ^_^ – user3001105 Mar 06 '14 at 21:16
  • I'd help you but I'm really busy at the moment... sorry. – Erik Kaplun Mar 06 '14 at 21:20
  • No problem, thanks for all your help thus far! All the try/exception examples are for python 2.x =( And that's prior to OSError... – user3001105 Mar 06 '14 at 21:26
  • Figured it out! Thanks again for you help and insight! ^_^ – user3001105 Mar 06 '14 at 21:43
0

You have recursion happening in your error handling

def login():
    #print('login')
    # Bind the socket
    try:
        s.connect((HOST, PORT))
        # Send login info
        s.send(bytes('NICK %s\r\n' % NICK, 'UTF-8'))
        s.send(bytes('USER %s %s bla :%s\r\n' % (IDENT, HOST, REALNAME), 'UTF-8'))
        s.send(bytes('JOIN %s\r\n' % CHAN, 'UTF-8'));
        print('Logging in...')
        chatlog('Logging in...')
    except:
        print('LOGIN_ERROR')
        login()

So in your function login() you have a try, then in the except you call login() again. This will just loop over and over again if the login fails.

Cory Kramer
  • 114,268
  • 16
  • 167
  • 218