View Single Post
Author Message
gubka
Veteran Member
Join Date: Jan 2012
Location: Russia
Old 04-03-2019 , 08:56   [ANY] New way to store data into the char array
Reply With Quote #1

That code use the pawn emit which originally not exist in sm compiler
More info about #emit here
Regards to komashchenko for restoring some removed features to a compiler and for the code below,
which show a simple example of what scripters can do with #emit, myself found it very useful for menu info , when you need to store some data like "4 5.0 -1" and now I don't use FormatEx and ExploadString and just simply send data via parameters and after extracting them back. Remember that any formatting on that stream char will break it, so only use the two function below, I hope the original sm once will return some of that kind of features because they might be useful in some situation, for example when you need to get the number of arguments which use sent to (any ...)

Use can send data like int, float by the AnyToStream(sBuf, 5, 5.0, 3, 5, 7) and get back using StreamToAny(sBuf, iData)
where iData is the any[]
Minimum size of char buffer array should be not less then args * 4 + 1
PHP Code:
/**
 * @brief Converts any parameter into a stream.
 *
 * @param sStream           Input string buffer.
 */
void AnyToStream(char[] sStreamany ...)
{
    
// Initialize some variables
    
int iArgsint nArg;
    
#emit load.s.pri 8
    #emit stor.s.pri iArgs
    
sStream[iArgs 4] = 0;
    
iArgs 12 iArgs 4;
    
    
// i = byte index
    
for(int i 16iArgs+= 4nArg++)
    {
        
#emit addr.alt 0
        #emit load.s.pri i
        #emit add
        #emit load.i
        #emit load.i
        #emit push.pri
        #emit load.s.pri nArg
        #emit smul.c 5
        #emit load.s.alt sStream
        #emit add
        #emit move.alt
        #emit pop.pri
        #emit stor.i
        #emit move.pri
        #emit add.c 4
        #emit move.alt
        #emit const.pri 16
        #emit strb.i 0x1
        
        
for(int x 0nArg 5!= 4x++)
        {
            if(
sStream[x] == 0)
            {
                
sStream[4] |= (1<<x);
                
sStream[x] = 0xFF;
            }
        }
    }
}

/**
 * @brief Converts the stream in an any array.
 *
 * @param sStream           Input stream buffer.
 * @param iBuffer           Output data array.
 */
int StreamToAny(char[] sStreamany[] iBuffer)
{
    
// Initialize some variables
    
int iCount strlen(sStream) / 5nTempiMagic;
    
    
// i = byte index
    
for(int i 0iCounti++)
    {
        
#emit load.s.alt sStream
        #emit load.s.pri i
        #emit smul.c 5
        #emit add
        #emit lodb.i 4
        #emit addr.alt nTemp
        #emit stor.i
        
        
if((iMagic sStream[4]) != 16)
        {
            if(
iMagic & (<< 0)) nTemp &= 0xFFFFFF00;
            if(
iMagic & (<< 1)) nTemp &= 0xFFFF00FF;
            if(
iMagic & (<< 2)) nTemp &= 0xFF00FFFF;
            if(
iMagic & (<< 3)) nTemp &= 0x00FFFFFF;
        }
        
        
iBuffer[i] = nTemp;
    }
    
    
// Return amount 
    
return iCount;

Some other lower performed examples:
Spoiler

GitHub
__________________

Last edited by gubka; 04-03-2019 at 16:54.
gubka is offline
Send a message via ICQ to gubka