Niko_boy

Untitled

Dec 11th, 2012
118
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 2.75 KB | None | 0 0
  1. stock FormatQuery(Format[], va_args<>)
  2. {
  3.     new
  4.         out[512];
  5.     va_format(out, sizeof(out), Format, va_start<1>);
  6.     return out;
  7. }
  8. //--- used like this
  9. print( FormatQuery("%s - %s AW %d %d %d %f", "ABC", "yo", 1, 2, 3 , 5.5) );
  10.  
  11. //=================
  12.  
  13. #define BYTES_PER_CELL 4
  14. // HUGE credit to ZeeX for finally cracking this problem:
  15. // [url=http://forum.sa-mp.com/index.php?topic=79810.msg901721#msg901721]http://forum.sa-mp.com/index.php?topic=79810.msg901721#msg901721[/url]
  16. stock FormatQuery2( fstring[], {Float, _}:...)
  17. {
  18.     // This is the number of parameters which are not variable that are passed
  19.     // to this function (i.e. the number of named parameters).
  20.     static const
  21.         STATIC_ARGS = 3;
  22.     // Get the number of variable arguments.
  23.     new
  24.         n = (numargs() - STATIC_ARGS) * BYTES_PER_CELL;
  25.     if(n)
  26.     {
  27.         new
  28.             message[144],
  29.             arg_start,
  30.             arg_end;
  31.  
  32.         // Load the real address of the last static parameter. Do this by
  33.         // loading the address of the last known static parameter and then
  34.         // adding the value of [FRM].
  35.         #emit CONST.alt        fstring
  36.         #emit LCTRL          5
  37.         #emit ADD
  38.         #emit STOR.S.pri        arg_start
  39.  
  40.         // Load the address of the last variable parameter. Do this by adding
  41.         // the number of variable parameters on the value just loaded.
  42.         #emit LOAD.S.alt        n
  43.         #emit ADD
  44.         #emit STOR.S.pri        arg_end
  45.  
  46.         // Push the variable arguments. This is done by loading the value of
  47.         // each one in reverse order and pushing them. I'd love to be able to
  48.         // rewrite this to use the values of pri and alt for comparison,
  49.         // instead of having to constantly load and reload two variables.
  50.         do
  51.         {
  52.             #emit LOAD.I
  53.             #emit PUSH.pri
  54.             arg_end -= BYTES_PER_CELL;
  55.             #emit LOAD.S.pri      arg_end
  56.         }
  57.         while(arg_end > arg_start);
  58.  
  59.         // Push the static format parameters.
  60.         #emit PUSH.S          fstring
  61.         #emit PUSH.C          144
  62.         #emit PUSH.ADR         message
  63.  
  64.         // Now push the number of arguments passed to format, including both
  65.         // static and variable ones and call the function.
  66.         n += BYTES_PER_CELL * 3;
  67.         #emit PUSH.S          n
  68.         #emit SYSREQ.C         format
  69.  
  70.         // Remove all data, including the return value, from the stack.
  71.         n += BYTES_PER_CELL;
  72.         #emit LCTRL          4
  73.         #emit LOAD.S.alt        n
  74.         #emit ADD
  75.         #emit SCTRL          4
  76.  
  77.         return print(message); // here D:\...pwn(390) : error 079: inconsistent return types (array & non-array)
  78.     }
  79.     return fstring;
  80. }
Advertisement
Add Comment
Please, Sign In to add comment