// File: gpertea[P]gclib/GStr.cpp
// Function: GStr::replace(char const*, char const*)
GStr&  GStr::replace(const char *rfrom, const char* rto) {
 if (length() == 0 || rfrom==NULL || strlen(rfrom)==0)
        return *this;
 unsigned int l=strlen(rfrom);
 unsigned int tl= (rto==NULL)?0:strlen(rto);
 make_unique(); //edit operation ahead
 char* p;
 char* dest;
 char* newdest=NULL;
 char* s = my_data->chars;
 if (tl!=l) { //reallocation
   if (tl>l) {  //possible enlargement
       GMALLOC(newdest, length()*(tl-l+1)+1);
       }
      else  {//delete or replace with a shorter string
       GMALLOC(newdest, length() + 1);
       }
      dest=newdest;
      if (tl==0) {//deletion
           while ((p=strstr(s,rfrom))!=NULL) {
               //rfrom found at position p
                memcpy(dest,s,p-s);
                dest+=p-s;
                s+=p-s+l; //s positioned in string after rfrom
                }
           //no more occurences, copy the remaining string
           strcpy(dest, s);
          }
        else { //replace with another string
          while ((p=strstr(s,rfrom))!=NULL) {
              memcpy(dest,s,p-s); //copy up rto the match
              dest+=p-s;
              memcpy(dest,rto,tl); //put the replacement string
              dest+=tl;
              s+=p-s+l;
              }
          //not found any more, copy rto end of string
          strcpy(dest, s);
          }
       Data* data=new_data(newdest);
       replace_data(data);
       GFREE(newdest);
       }
  else { //inplace editing: no need rto reallocate
    while ((p=strstr(s,rfrom))!=NULL) {
        memcpy(p,rto,l);
        s+=p-s+l;
        }
   }
 return *this;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x60, %rsp
movq %rdi, -0x10(%rbp)
movq %rsi, -0x18(%rbp)
movq %rdx, -0x20(%rbp)
movq -0x10(%rbp), %rdi
movq %rdi, -0x58(%rbp)
callq 0xb660
cmpl $0x0, %eax
je 0x94ec
cmpq $0x0, -0x18(%rbp)
je 0x94ec
movq -0x18(%rbp), %rdi
callq 0x2140
cmpq $0x0, %rax
jne 0x94f9
movq -0x58(%rbp), %rax
movq %rax, -0x8(%rbp)
jmp 0x9746
movq -0x18(%rbp), %rdi
callq 0x2140
movl %eax, -0x24(%rbp)
cmpq $0x0, -0x20(%rbp)
jne 0x9514
xorl %eax, %eax
movq %rax, -0x60(%rbp)
jmp 0x9521
movq -0x20(%rbp), %rdi
callq 0x2140
movq %rax, -0x60(%rbp)
movq -0x58(%rbp), %rdi
movq -0x60(%rbp), %rax
movl %eax, -0x28(%rbp)
callq 0x63e0
movq -0x58(%rbp), %rax
movq $0x0, -0x40(%rbp)
movq 0x20(%rax), %rax
addq $0xc, %rax
movq %rax, -0x48(%rbp)
movl -0x28(%rbp), %eax
cmpl -0x24(%rbp), %eax
je 0x96f6
movl -0x28(%rbp), %eax
cmpl -0x24(%rbp), %eax
jbe 0x9596
movq -0x58(%rbp), %rdi
callq 0xb660
movl -0x28(%rbp), %ecx
subl -0x24(%rbp), %ecx
addl $0x1, %ecx
imull %ecx, %eax
addl $0x1, %eax
movl %eax, %eax
movl %eax, %esi
leaq -0x40(%rbp), %rdi
callq 0x58f0
testb $0x1, %al
jne 0x9594
leaq 0xaa96(%rip), %rdi      # 0x14023
movb $0x0, %al
callq 0x2640
jmp 0x95c2
movq -0x58(%rbp), %rdi
callq 0xb660
addl $0x1, %eax
movslq %eax, %rsi
leaq -0x40(%rbp), %rdi
callq 0x58f0
testb $0x1, %al
jne 0x95c0
leaq 0xaa6a(%rip), %rdi      # 0x14023
movb $0x0, %al
callq 0x2640
jmp 0x95c2
movq -0x40(%rbp), %rax
movq %rax, -0x38(%rbp)
cmpl $0x0, -0x28(%rbp)
jne 0x9641
jmp 0x95d2
movq -0x48(%rbp), %rdi
movq -0x18(%rbp), %rsi
callq 0x2090
movq %rax, -0x30(%rbp)
cmpq $0x0, %rax
je 0x962f
movq -0x38(%rbp), %rdi
movq -0x48(%rbp), %rsi
movq -0x30(%rbp), %rdx
movq -0x48(%rbp), %rax
subq %rax, %rdx
callq 0x21f0
movq -0x30(%rbp), %rax
movq -0x48(%rbp), %rcx
subq %rcx, %rax
addq -0x38(%rbp), %rax
movq %rax, -0x38(%rbp)
movq -0x30(%rbp), %rax
movq -0x48(%rbp), %rcx
subq %rcx, %rax
movl -0x24(%rbp), %ecx
addq %rcx, %rax
addq -0x48(%rbp), %rax
movq %rax, -0x48(%rbp)
jmp 0x95d2
movq -0x38(%rbp), %rdi
movq -0x48(%rbp), %rsi
callq 0x2240
jmp 0x96cf
jmp 0x9643
movq -0x48(%rbp), %rdi
movq -0x18(%rbp), %rsi
callq 0x2090
movq %rax, -0x30(%rbp)
cmpq $0x0, %rax
je 0x96c2
movq -0x38(%rbp), %rdi
movq -0x48(%rbp), %rsi
movq -0x30(%rbp), %rdx
movq -0x48(%rbp), %rax
subq %rax, %rdx
callq 0x21f0
movq -0x30(%rbp), %rax
movq -0x48(%rbp), %rcx
subq %rcx, %rax
addq -0x38(%rbp), %rax
movq %rax, -0x38(%rbp)
movq -0x38(%rbp), %rdi
movq -0x20(%rbp), %rsi
movl -0x28(%rbp), %eax
movl %eax, %edx
callq 0x21f0
movl -0x28(%rbp), %ecx
movq -0x38(%rbp), %rax
movl %ecx, %ecx
addq %rcx, %rax
movq %rax, -0x38(%rbp)
movq -0x30(%rbp), %rax
movq -0x48(%rbp), %rcx
subq %rcx, %rax
movl -0x24(%rbp), %ecx
addq %rcx, %rax
addq -0x48(%rbp), %rax
movq %rax, -0x48(%rbp)
jmp 0x9643
movq -0x38(%rbp), %rdi
movq -0x48(%rbp), %rsi
callq 0x2240
movq -0x40(%rbp), %rdi
xorl %esi, %esi
callq 0x6190
movq -0x58(%rbp), %rdi
movq %rax, -0x50(%rbp)
movq -0x50(%rbp), %rsi
callq 0x6460
leaq -0x40(%rbp), %rdi
callq 0x5a90
jmp 0x973e
jmp 0x96f8
movq -0x48(%rbp), %rdi
movq -0x18(%rbp), %rsi
callq 0x2090
movq %rax, -0x30(%rbp)
cmpq $0x0, %rax
je 0x973c
movq -0x30(%rbp), %rdi
movq -0x20(%rbp), %rsi
movl -0x24(%rbp), %eax
movl %eax, %edx
callq 0x21f0
movq -0x30(%rbp), %rax
movq -0x48(%rbp), %rcx
subq %rcx, %rax
movl -0x24(%rbp), %ecx
addq %rcx, %rax
addq -0x48(%rbp), %rax
movq %rax, -0x48(%rbp)
jmp 0x96f8
jmp 0x973e
movq -0x58(%rbp), %rax
movq %rax, -0x8(%rbp)
movq -0x8(%rbp), %rax
addq $0x60, %rsp
popq %rbp
retq