0

Sooo... I have written a plugin, and the whole plugin works fine. ONLY PROBLEM: My TS3 Client crashes.

To give a context:

(Warning: That code is just poorly pasted. On GitHub, it crashes at line 270 and 285)

// Helper Function

    String^ getChannelName(uint64 serverConnectionHandlerID, uint64 channelID) {
        char* tmp;
        if (ts3Functions.getChannelVariableAsString(serverConnectionHandlerID, channelID, CHANNEL_NAME, &tmp) == ERROR_ok) {
            return marshal_as<String^>(tmp);
        }
        else
        {
            return "ERROR_GETTING_CHANNELNAME";
        }
    }
    void assemble_a() {
        List<String^>^ clients;
        List<String^>^ channel;

        // Some middlepart here, but I made sure it works as it should

        // And the actual part where it is crashing
        if (resChL == ERROR_ok) {
            for (int i = 0; channelListPtr[i]; ++i) {
                String^ a = getChannelName(schid, channelListPtr[i]);
                const char* b = (const char*)(Marshal::StringToHGlobalAnsi(a)).ToPointer();
                ts3Functions.logMessage(b, LogLevel_DEBUG, "DEBUG_VC", schid);
                if (String::IsNullOrEmpty(a) == false) {
                    channel->Add(a); // It crashes RIGHT at this point
                }
            }
        }
    }

So I am asking on the TS3 forum for a long time, got a lot of answers, and noone could tell me why it actually crashes, and I didn't manage to figure it out on my own either.

It does actually print the channel name [*spacer0]t but as soon as it should append it to the String List, it crashes. It throws the message The thread has tried to write or read from a virtual address that it does not have the accesspermissions for.

I seriously have no idea what to do, trying to fix it now for over 2 weeks.

For full context: GitHub Sourcecode

Sorry if this question MIGHT be a little out of topic here (Is it? I don't know...) but I don't really know what to do with that problem anymore...

EDIT: Errormessage from try/catch is: System.NullReferebceException: The Objectreference was not set to the Objectinstance, occured in tsapi.assembleGrammar()

Community
  • 1
  • 1
J.Horr
  • 77
  • 1
  • 10
  • System.NullReferebceException: The Objectreference was not set to the Objectinstance, occured in tsapi.assembleGrammar() – J.Horr Mar 15 '17 at 17:05

1 Answers1

1
List<String^>^ channel;
...
channel->Add(a);

channel is null. You need to initialize it with something, probably gcnew List<String^>(). I'm not sure why you're getting an access denied message instead of NullReferenceException.

Other issues

  • Make sure you're handling all the unmanaged strings properly. For example, does getChannelVariableAsString require a call to explicitly free the buffer? Be absolutely sure to call FreeHGlobal to free the memory that StringToHGlobalAnsi allocated for you.
David Yaw
  • 25,725
  • 4
  • 59
  • 90
  • The strings are fine, I made that sure. I am using marshal_as<>() and StringToHGlobalAnsi() – J.Horr Mar 15 '17 at 17:07
  • 1
    The strings are not fine, you're only calling `FreeHGlobal` in one of the three spots where you're calling `StringToHGlobalAnsi`. This is a memory leak. – David Yaw Mar 15 '17 at 17:10
  • Really?? Well, I was working on changing the StringToHGlobal to marshal_as<>() – J.Horr Mar 15 '17 at 17:30
  • 1
    Using marshal_as to convert to either std::string or char* with a marshal_context would also solve the memory leak. – David Yaw Mar 15 '17 at 17:32
  • The thing is, I cannot find more than one case where I used StringToHGlobalAnsi(), and I did free it there. So I guess it is fine then? – J.Horr Mar 15 '17 at 17:46
  • 1) In this question. 2) https://github.com/WhOoKie/TS3WKVC/blob/master/plugin.cpp#L267 3) https://github.com/WhOoKie/TS3WKVC/blob/master/plugin.cpp#L282 – David Yaw Mar 15 '17 at 17:51
  • Alright, I removed those anyways now, those were just used for debugging. – J.Horr Mar 15 '17 at 18:01