* Added r_parse plugin for mandingo's mreplace

This commit is contained in:
Nibble 2009-02-26 02:31:03 +01:00
parent 801ed768fc
commit 1d5162d8e3
7 changed files with 469 additions and 2 deletions

View File

@ -7,6 +7,8 @@
#include <list.h>
#define R_PARSE_STRLEN 256
struct r_parse_t {
void *user;
struct r_parse_handle_t *cur;

View File

@ -1,6 +1,8 @@
CFLAGS=-I../../include -I../arch/ -I../arch/include -Wall -fPIC -shared -Wl,-R..
all: parse_dummy.so parse_x86_pseudo.so
OBJ_MREPLACE=mreplace/mreplace.o mreplace/mmemory.o
all: parse_dummy.so parse_x86_pseudo.so parse_mreplace.so
@true
parse_dummy.so:
@ -11,5 +13,9 @@ parse_x86_pseudo.so: parse_x86_pseudo.o
${CC} ${CFLAGS} -o parse_x86_pseudo.so parse_x86_pseudo.o
@#strip -s parse_x86_pseudo.so
parse_mreplace.so: parse_mreplace.o ${OBJ_MREPLACE}
${CC} ${CFLAGS} -o parse_mreplace.so parse_mreplace.o ${OBJ_MREPLACE}
@#strip -s parse_mreplace.so
clean:
-rm -f *.so *.o
-rm -f *.so *.o ${OBJ_MREPLACE}

View File

@ -0,0 +1,114 @@
//
// Library: Memory Manage Module v1.10, Copyleft, 2009-02-25
// Author : Mandingo, mandingo [ at ]yoire.com
//
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <malloc.h>
#include "mmemory.h"
memInfo *mInfo;
void memStringRealloc(memChunk *chunk){
memCheckState();
memChunk *temp;
temp=memString(chunk->address);
//printf("Reallocating chunk size %d to size %d\n",chunk->size,temp->size);
memCopy(chunk,temp);
memFree(temp);
}
void memFree(memChunk *chunk){
memCheckState();
if(chunk && chunk->address){
mInfo->allocated-=chunk->size;
free(chunk->address);
free(chunk);
}
}
void memInit(){
mInfo=(memInfo*)malloc(sizeof(memInfo));
bzero(mInfo,sizeof(memInfo));
mInfo->state=MEM_STATE_OK;
mInfo->allocated+=sizeof(memInfo);
}
void memCheckState(){
if(mInfo==NULL) memInit();
if(mInfo->state!=MEM_STATE_OK){
fprintf(stderr,"\rMMemmory not initialized :p\n");
exit(0);
}
}
memInfo *memInformation(){
memCheckState();
return mInfo;
}
long memAllocated(){
memCheckState();
return mInfo->allocated;
}
memChunk *memReserve(long size){
static memChunk *buffer;
memCheckState();
buffer=(memChunk*)malloc(sizeof(memChunk));
if((buffer->address=(char*)malloc(size))==NULL){
perror("memReserve");
exit(0);
}
//printf("- reservando %d bytes\n",size);
buffer->size=size;
bzero(buffer->address,buffer->size);
mInfo->allocated+=size;
return buffer;
}
memChunk *memStringReserve(char *string,long nbytes){
static memChunk *buffer;
buffer=memReserve(nbytes);
memCopy(buffer,memString(string));
return buffer;
}
memChunk *memString(char *string){
static memChunk *buffer;
memCheckState();
buffer=memReserve(strlen(string)+1);
#if USE_BCOPY
bcopy(string,buffer->address,strlen(string));
#else
memcpy(buffer->address,string,strlen(string));
#endif
return buffer;
}
void memCopy(memChunk *dest,memChunk *source){
long nbytes;
if(!dest->address){
dest=memString(source->address);
}else{
nbytes=dest->size > source->size ? source->size : dest->size;
memCheckState();
//printf("Copying %d bytes to dest (size %d)\n",nbytes,dest->address,dest->size);
#if USE_BCOPY
bcopy(source->address,dest->address,nbytes);
#else
memcpy(dest->address,source->address,nbytes);
#endif
}
}
void memStrCat(memChunk *dest,char *string){
long nbytes;
memChunk result,*temp;
temp = memReserve(dest->size+strlen(string)+1);
result.address = dest->address+strlen(dest->address);
result.size = dest->size-strlen(dest->address)+1;
memCopy(temp,memString(string));
memCopy(&result,temp);
memFree(temp);
}

View File

@ -0,0 +1,32 @@
//
// Library: Memory Manage Module v1.10, Copyleft, 2009-02-25
// Author : Mandingo, mandingo [ at ]yoire.com
//
#define USE_BCOPY 1
#define MEM_STATE_BAD 0
#define MEM_STATE_OK 1
typedef struct {
char *address;
long size;
} memChunk;
typedef struct {
long allocated;
char state;
} memInfo;
memChunk *memReserve(long size);
void memCopy(memChunk *dest,memChunk *source);
void memStrCat(memChunk *dest,char *string);
memInfo *memInformation();
long memAllocated();
void memFree(memChunk *chunk);
void memCheckState();
memChunk *memString(char *string);
void memStringRealloc(memChunk *chunk);
memChunk *memStringReserve(char *string,long nbytes);

View File

@ -0,0 +1,252 @@
//
// Library: Experimental PERL alike "search & replace", Copyleft, 2009-02-20
// Author : Mandingo, mandingo [ at ]yoire.com
//
#include <regex.h>
#include <stdio.h>
#include <string.h>
#include <malloc.h>
#include <stdlib.h>
#include "mmemory.h"
#include "mreplace.h"
#if !defined DEBUG2
#define DEBUG2 0
#endif
#if defined LIB
#include "m2c_api20.h"
#else
#define DBG(func,...) "";
#endif
#define CHECKS_CHUNCK_SIZE 1024
#define CHECKS_CHUNCK_COUNT 6
int matchs(const char *string, char *pattern)
{
int status;
regex_t re;
if (regcomp(&re, pattern, REG_EXTENDED|REG_NOSUB) != 0) return(0);
status = regexec(&re, string, (size_t) 0, NULL, 0);
regfree(&re);
if (status != 0) return(0);
return(1);
}
void sreplace(char *s,char *orig,char *rep,char multi,long dsize){
char *p;
memChunk *buffer,*string,*result;
if(!(p=strstr(s, orig))) return;
buffer=memReserve(dsize);
string=memString(s);
memCopy(buffer, string);
snprintf(buffer->address+(p-s), buffer->size-(p-s),"%s%s", rep, p+strlen(orig));
result=memString(buffer->address);
strcpy(s,result->address); //unsafe
memFree(string);
memFree(result);
memFree(buffer);
}
char *mreplace(char *string, char *se,char *rep)
{
int status,m,i;
char *s;
regex_t re;
size_t nmatch = 16;
regmatch_t pm[nmatch];
char regError[64],*p;
ulong offset = 0;
char field[16];
char *sData;
memChunk *result,*temp,*found,*ffound;
char *search;
if(!string) return "";
if(!strlen(se)) return string;
if(!strcmp(se,rep)) return string;
temp=memStringReserve(string,INPUTLINE_BUFFER_REPLACE_SIZE);
#if DEBUG2
sData=strdup(string);
DBG("mreplace(string,se,re)","string : %s",sData);
DBG("mreplace(string,se,re)","search : %s",se);
DBG("mreplace(string,se,re)","replace : %s",replace);
#endif
p=(char*)string;
search=strdup(se);
if(matchs(search,"\\d")) sreplace(search,"\\d","[0-9]\0",1,6);
if(regcomp(&re, search, REG_EXTENDED) != 0) if(regcomp(&re, search, REG_EXTENDED<<1)) return (char*)string;
if(status = regexec(&re, string, nmatch, pm, 0)) return (char*)string;
found = memReserve(INPUTLINE_BUFFER_REPLACE_SIZE);
ffound = memReserve(INPUTLINE_BUFFER_REPLACE_SIZE);
while(!status){
offset=strlen(temp->address)-strlen(string);
snprintf(found->address,INPUTLINE_BUFFER_REPLACE_SIZE,"%.*s",pm[0].rm_eo - pm[0].rm_so, &string[pm[0].rm_so],&string[pm[0].rm_so]);
#if DEBUG2
printf("------->> found \"%s\" length => %d offset[%d]\n",
found->address,
strlen(temp),offset);
#endif
sreplace(temp->address+offset,found->address,rep,0,INPUTLINE_BUFFER_REPLACE_SIZE-offset);
for(i=1;i<nmatch;i++){
snprintf(ffound->address,INPUTLINE_BUFFER_REPLACE_SIZE,"%.*s",pm[i].rm_eo - pm[i].rm_so, &string[pm[i].rm_so],&string[pm[i].rm_so]);
snprintf(field,sizeof(field),"\\%d",i);
if(strlen(ffound->address)) {
sreplace(temp->address,field,ffound->address,1,INPUTLINE_BUFFER_REPLACE_SIZE);
}else{
sreplace(temp->address,field,"",1,INPUTLINE_BUFFER_REPLACE_SIZE);
continue;
}
#if DEBUG2
printf(">> subfound %2d '%s' => '%s' length %d\n",
i,
ffound->address,
temp->address,offset);
#endif
}
if(offset<0) offset=-offset;
if(*string && strlen(string+pm[0].rm_eo)) {
string+=pm[0].rm_eo;
status = regexec(&re, string, nmatch, pm, 0);
}else{
status=-1;
}
}
#if DEBUG2
DBG("mreplace(string,se,re)","result : %s",temp->address);
#endif
memFree(found);
memFree(ffound);
result=memString(temp->address);
memFree(temp);
return result->address;
}
char *treplace(char *data,char *search,char *replace){
long offset=0,f;
char line[INPUTLINE_BUFFER_REPLACE_SIZE],*newline,*p;
memChunk *result;
ulong resultAllocSize;
#if DEBUG2
DBG("treplace(string,se,re)","string : %s",data);
DBG("treplace(string,se,re)","search : %s",search);
DBG("treplace(string,se,re)","replace : %s",replace);
#endif
if(!strlen(data)) return data;
if(!strlen(search)) return data;
//memFree(result);
result=memReserve(INPUTLINE_BUFFER_REPLACE_SIZE);
p=data;
while(sscanf(p,"%[^\n]",line)==1){
if(p-data>strlen(data)) break;
newline=mreplace(line,search,replace);
memStrCat(result,newline);
if(*(p+strlen(line))) memStrCat(result,"\n");else break;
p+=strlen(line)+1;
}
memStringRealloc(result);
return result->address;
}
void doChecks(){
char *checkBuffer,*checkresult,*sIn;
long i,n,total,invalid=0;
typedef struct {char *in,*s,*r,*out;} sCheck;
sCheck checks[]={
{"{{div.cOptions}}go {{tag.tag56}} {{get.link.parent.html}}/ edit {{tag.tag57}} / edit {{tag.tag58}} / rename {{tag.tag59}} / move {{tag.tag60}} / add {{tag.tag61}}{{get.delete.html}} / {{get.link.login.html}}{{enddiv}}", ".*(\\{\\{\\w+\\.\\w+(\\.\\w+)?\\}\\}).*","\\1","{{get.delete.html}}"},
{"abracadabra", "a", "b", "bbrbcbdbbrb"},
{"a1a2a3a4a5a", "\\d", "_", "a_a_a_a_a_a"},
{"z1b4a5a", "(\\w)", "[\\1]", "[z][1][b][4][a][5][a]"},
{"farooeboar", "(.)..(..).(.).", "\\1\\2\\3", "foobar"},
{"file.c", "(([^\\.]+)\\.(.+))", "[\\1] name=\\2 ext=\\3", "[file.c] name=file ext=c"},
{"helloworld", "([e-o])", "_\\1_", "_h__e__l__l__o_w_o_r_l_d"},
{"I' a {{get.tag}}",".*(\\{\\{\\w+\\.\\w+(\\.\\w+)?\\}\\}).*","found tag \"\\1\"","found tag \"{{get.tag}}\""},
{"get.param","(\\w+?)\\..+","method is \"\\1\"","method is \"get\""},
{"get.param","[^\\.]+\\.([^\\.]+).*","tagname is \"\\1\"","tagname is \"param\""}
};
total=sizeof(checks)/sizeof(checks[0])-1;
if((checkBuffer=(char*)malloc(CHECKS_CHUNCK_COUNT*CHECKS_CHUNCK_SIZE))==NULL){
perror("malloc");
}else{
memset(checkBuffer,0,CHECKS_CHUNCK_COUNT*CHECKS_CHUNCK_SIZE);
}
fprintf(stdout," [+] Performing several replacements to check consistence ");
for(n=0;n<100;n++){
if(!(n%25)){
printf(".");
fflush(stdout);
}
for(i=0;i<total;i++){
checkresult=treplace(checks[i].in,checks[i].s,checks[i].r);
sIn=strdup(checks[i].in);
if(strlen(sIn)>20) memcpy(sIn+15," ...\0",5);
if(strcmp(checkresult,checks[i].out)){
fprintf(stderr,"\r[%d/%d] %-20s s: %-30s r: %-20s => %-25s ",i+1,total,sIn,checks[i].s,checks[i].r,checkresult);
fprintf(stdout," ERR :(\n");
exit(0);
}else{
if(!n){
fprintf(stderr,"\r[%d/%d] %-20s s: %-30s r: %-20s => %-25s ",i+1,total,sIn,checks[i].s,checks[i].r,checkresult);
fprintf(stdout," OK :)\n");
}
}
}
}
for(n=1;n<=CHECKS_CHUNCK_COUNT;n+=1+CHECKS_CHUNCK_COUNT/10){
fprintf(stdout,"\r[ + ] Checking stability for different input sizes consistence %d bytes, memory allocated: %d bytes",n*CHECKS_CHUNCK_COUNT*CHECKS_CHUNCK_SIZE,memAllocated());
fflush(stdout);
memset(checkBuffer,'.',n*CHECKS_CHUNCK_SIZE-1);
checkBuffer[n*CHECKS_CHUNCK_SIZE]=0;
mreplace(checkBuffer,"\\.","_");
treplace(checkBuffer,"_",".");
}
fprintf(stdout,"\n");
fprintf(stdout,"[ m ] Memory allocated final: %d bytes\n",memAllocated());
}
#if !defined LIB
/*
builds a binary for command line "search & replace" tests
*/
int main(char argc,char **argv){
if(argc==4 && strlen(argv[2])){
#if DEBUG2
printf("Input string: %s, length %d, search %s, replace %s\n",argv[1],strlen(argv[1]),argv[2],argv[3]);
#endif
fprintf(stdout,"%s\n",treplace(argv[1],argv[2],argv[3]));
}else{
fprintf(stdout, "Perl alike \"search & replace\" v1.01 by Mandingo, Copyleft, 2009\n");
doChecks();
fprintf(stdout, "Usage: %s \"<text>\" \"<search>\" \"<replace>\"\n",argv[0]);
}
return 1;
}
#endif

View File

@ -0,0 +1,17 @@
//
// Library: Experimental PERL alike "search & replace", Copyleft, 2009-02-20
// Author : Mandingo, mandingo [ at ]yoire.com
//
#if !defined INPUTLINE_BUFFER_REPLACE_SIZE
#define INPUTLINE_BUFFER_REPLACE_SIZE 32768
#endif
//search & replace strings - no regexp
extern void sreplace(char *s,char *orig,char *rep,char multi,long dsize);
//search & replace strings - regexp + multiline safe
extern char *treplace(char *string,char *search,char *replace);
extern char *mreplace(char *string, char *se,char *replace);

View File

@ -0,0 +1,44 @@
/* radare - LGPL - Copyright 2009 nibble<.ds@gmail.com> */
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "mreplace/mreplace.h"
#include <r_types.h>
#include <r_lib.h>
#include <r_util.h>
#include <r_parse.h>
struct mreplace_t {
char *data;
char *search;
char *replace;
};
static int parse(struct r_parse_t *p, void *data, char *str)
{
struct mreplace_t *sdata = (struct mreplace_t*)data;
char *buf = NULL;
buf = treplace(sdata->data, sdata->search, sdata->replace);
memcpy(str, buf, R_PARSE_STRLEN);
if (buf != NULL)
free(buf);
return R_TRUE;
}
static struct r_parse_handle_t r_parse_plugin_parse_mreplace = {
.name = "parse_mreplace",
.desc = "mreplace parsing plugin",
.init = NULL,
.fini = NULL,
.parse = &parse,
};
struct r_lib_struct_t radare_plugin = {
.type = R_LIB_TYPE_PARSE,
.data = &r_parse_plugin_parse_mreplace
};