Macro redefinition work-around
#6

Took some time to finish what you posted above today. I don't know what you meant by it was very incomplete, it only took me a few minutes and a couple extra lines to finish it up! Doesn't include the distinction between strings and arrays, or other types yet, but this was just a small prototype.
pawn Код:
#define OF::%0(%1) static stock __%0__(){return _:SPF0:SPF1:0;}of_%0_(%1,)

// Check for parameters - if none, return immediately; otherwise, split for further parsing
#define SPF0:SPF1:0;}%0(,) 0;}%0()
#define SPF1:0;}%0(%1,%2) SPF2:SPF3:SPF4:SPF5:0;}%0(|||%1|||%2)

// Add checking for strings and ints - this assumes there are two+ parameters left
#define SPF2:SPF3:SPF4:SPF5:0;}%0(%9|||%1[]|||%2,%3) SPF2:SPF3:SPF4:SPF5:0;}%0s(%9%1[],|||%2|||%3)
#define SPF3:SPF4:SPF5:0;}%0(%9|||%1|||%2,%3) SPF2:SPF3:SPF4:SPF5:0;}%0i(%9%1,|||%2|||%3)

// Add checking for strings and ints - this assumes only one parameter is left
#define SPF4:SPF5:0;}%0(%9|||%1[]|||) 0;}%0s(%9%1[])
#define SPF5:0;}%0(%9|||%1|||) 0;}%0i(%9%1)
It works well, besides one small warning. The "holder functions" that is used to return all the tags is continually re-defined (as this is for overloaded functions). I've tried a few things to get it to work, one being #undef the function (__%0__) inside the function body itself before the return, but it seemed to have no effect. I also tried altering the function (__%0__) to include some distinction based on the parameters, but then again no tags could be used, so I'm stuck there. A final plausible solution I had was to #undef it inside the actual body of the final created function (of_Test_%1), but it got conflicted as it required me searching for an ending curly bracket, which developed issues in syntax:
pawn Код:
OF::Test(int) {
}
OF::Test(int)
{
}
// etc
Finally, I thought of creating a second unique functions (based on the specifiers returned at the end) whose only purpose was to #undef the original holder function (__%0__). This created code like so:
pawn Код:
// NOT COMPLETE NOR WORKS, JUST AN EXAMPLE
#define OF::%0(%1) static stock __%0__(){return _:SPF0:SPF1:0;}stock __%0_(){#undef __%0__}of_%0_(%1,)

// Check for parameters - if none, return immediately; otherwise, split for further parsing
#define SPF0:SPF1:0;}%0__%1_(){%2}%3(,) 0;}%0__%1_(){%2}%3()
#define SPF1:0;}%0__%1_(){%2}%3(%4,%5) SPF2:SPF3:SPF4:SPF5:0;}%0__%1_(){%2}%3(|||%4|||%5)

// Add checking for strings and ints - this assumes there are two+ parameters left
#define SPF2:SPF3:SPF4:SPF5:0;}%0__%1_(){%2}%3(%9|||%4[]|||%5,%6) SPF2:SPF3:SPF4:SPF5:0;}%0__%1_(){%2}%3s(%9%4[],|||%5|||%6)
#define SPF3:SPF4:SPF5:0;}%0__%1_(){%2}%3(%9|||%4|||%5,%6) SPF2:SPF3:SPF4:SPF5:0;}%0__%1_(){%2}%3i(%9%4,|||%5|||%6)

// Add checking for strings and ints - this assumes only one parameter is left
#define SPF4:SPF5:0;}%0__%1_(){%2}%3(%9|||%4[]|||) SPF99:0;}%0__%1_(){%2}%3s(%9%4[])
#define SPF5:0;}%0__%1_(){%2}%3(%9|||%4|||) SPF99:0;}%0__%1_(){%2}%3i(%9%4)

// Final - create the function to undefine the original "holder" function
#define SPF99:0;}%0__%1_(){%2}%3(%4) 0;}%0__%1_%3(){%2}(%4)
However, I soon realized that that unique function would actually never be called from that definition, so would need to go inside another function. The only way to do that without creating an infinite loop would be to have it called in the final function (of_Test_%1), but again, that would lead to the issue of syntax.

I'm still searching for a way to make that work, but if you have any suggestions, please let me know!

P.S. I actually just found something that confuses me. Perhaps you could give me some insight onto why this is happening?
pawn Код:
Test() {}

stock _Test()
{
    #undef Test
}

main()
{
    _Test();
    #if defined Test
        print("IT IS STILL ALIVE");
    #else
        print("IT HAS BEEN TAKEN");
    #endif
}
This code will give me the following errors/warnings:
Код:
(60) : error 017: undefined symbol "Test"
(60) : error 029: invalid expression, assumed zero
(60 -- 61) : error 076: syntax error in the expression, or invalid function call
(60 -- 61) : fatal error 107: too many error messages on one line
This is saying, as far as I can understand, that Test() {} is not being defined with the symbol name of "Test", but something else. However, if I change the code to the following:
pawn Код:
Test() {}

stock _Test()
{
    #undef MAX_PLAYERS
}

main()
{
    _Test();
    #if defined Test
        print("IT IS STILL ALIVE");
    #else
        print("IT HAS BEEN TAKEN");
    #endif
}
It only throws this one warning:
Код:
(72) : warning 203: symbol is never used: "Test"
Which is saying that it IS defined with the symbol "Test".
Reply


Messages In This Thread
Macro redefinition work-around - by Bakr - 02.03.2013, 22:53
Re: Macro redefinition work-around - by Bakr - 02.03.2013, 23:19
Re: Macro redefinition work-around - by Bakr - 04.03.2013, 00:50
Re: Macro redefinition work-around - by Bakr - 04.03.2013, 10:24
Re: Macro redefinition work-around - by Bakr - 05.03.2013, 10:20
Re: Macro redefinition work-around - by Bakr - 06.03.2013, 19:18

Forum Jump:


Users browsing this thread: 1 Guest(s)