Obfuscation

[quote=92833:@Kem Tekinay]I just did. No difference.

[/quote]

That’s where I was hoping an integer array would remove the visible strings from the binary and store the values within the compiled method. Much harder to track down with a hex editor…

I don’t think so Jim. If you store 65 to an integer array, that’s still going to show up as “A” in a hex editor. That’s why I recommended adding random values to the codes.

[quote=92791:@jim mckay]A hacker could still find the info with a breakpoint, etc… but I’d like a simple way to obfuscate things…
[/quote]
If you ever have to decode the obfuscated data into a string representation then they can find it
Best off to NOT have to ever do that if you can avoid it

If the thing you have to obfuscate is, say, a plug-in serial number, do you have another suggestion?

[quote=92848:@Kem Tekinay]If the thing you have to obfuscate is, say, a plug-in serial number, do you have another suggestion?
[/quote]

Honestly, Kem, if it’s someone else’s plugin, use the obfuscation scheme they they supply. Why? Because whatever obfuscation of said serial number you decide to use does absolutely no good in practice to prevent disclosure. Might as well just CYA and do it how they think it should be done. These registration systems are simply only capable of keeping honest people honest. The cost to be dishonest is not high. The capabilities required are also not high.

And to bring it full circle to the previous thread… Anyone who grasped this very basic fact would see that either through malicious intent or gross incompetence while claiming knowledge and purpose, what Matthew did and how he presented it was unhelpful to the cause of keeping honest people honest in this community. The bottom line deal is that however we add-on devs choose to “protect” our add-ons, we are ultimately relying on people to just do the right thing, and we should foster a market where that’s encouraged. We should not tolerate malicious efforts or sheer incompetence which have the obvious effect of encouraging people to not do the right thing.

I can’t speak for Norman, but consider using the infamous “write-only” database to fully secure your data! :wink:

I still prefer to roll up the windows and lock the doors, and maybe throw in a steering wheel lock.

My question to Norman remains…

So does the lovely tool that @Bob Keeney offers Obfuscate stand up well to strings and other such string revealing tools?

Hex editors, sure. Low level debuggers that examine memory and stack, absolutely not. The latter are not difficult to use, nor are they obscure.

Jim, I hope you don’t mind, but I took your idea, added my “adder” suggestion, and turned it into an IDE script. The result from the script:

  'Encoding for value: [&]8[&]
  
  dim codeArr() as Integer = Array( 83398, 85617, 94740, 83765, 95503, 73168, 79147 )
  dim adderArr() as Integer = Array( 83307, 85524, 94702, 83674, 95465, 73112, 79054 )
  dim indexArr() as Integer = Array( 4, 2, 1, 0, 5, 3, 6 )
  indexArr.SortWith codeArr, adderArr
  
  dim decodedChars() as String
  for i as Integer = 0 to codeArr.Ubound
    decodedChars.Append Chr( codeArr( i ) - adderArr( i ) )
  next i
  
  dim decodedString as String = Join( decodedChars, "" )

That looks entirely like gibberish in a hex editor.

To be technical about it, it is spelled “libgishlickly”.

Here is the script:

  Function RndInRange (startIndex As Integer, endIndex As Integer) As Integer
    dim d as Double = Rnd
    dim range as Integer = endIndex - startIndex
    return Round( range * d ) + startIndex
  End Function
  
  dim origString as String = SelText
  if origString.Trim = "" then
    print "Select some text first."
    return
  end if
  
  dim chars() as String = Split( origString, "" )
  
  dim startQuote as boolean = chars( 0 ) = """"
  dim endQuote as boolean = chars( chars.Ubound ) = """"
  
  if endQuote then
    chars.Remove chars.Ubound
  end if
  
  if chars.Ubound <> -1 and startQuote then
    chars.Remove 0
  end if
  
  if chars.Ubound = -1 then
    print "Select some valid text first."
    return
  end if
  
  dim stringToEncode as String = Join( chars, "" )
  dim b as String = ShowDialog( "You are about to encode this string. Proceed?", stringToEncode, "Yes", "No", "" )
  if b = "No" then
    return
  end if
  
  dim index as Integer
  dim codeArr() as String
  dim indexArr() as String
  dim addArr() as String
  dim randomizerArr() as Integer
  for index = 0 to chars.Ubound
    dim thisAdd as Integer = RndInRange( 64001, 100000 )
    codeArr.Append Str( Asc( chars( index ) ) + thisAdd )
    indexArr.Append Str( index )
    addArr.Append Str( thisAdd )
    randomizerArr.Append RndInRange( 0, chars.Ubound * 100 )
  next index
  
  randomizerArr.SortWith( codeArr, indexArr, addArr )
  
  // Construct the code
  dim eol as String = EndOfLine
  dim resultArr() as String
  
  resultArr.Append "'Encoding for value: "
  resultArr.Append stringToEncode
  resultArr.Append eol
  resultArr.Append eol
  
  resultArr.Append "dim codeArr() as Integer = Array( "
  resultArr.Append Join( codeArr, ", " )
  resultArr.Append " )"
  resultArr.Append eol
  
  resultArr.Append "dim adderArr() as Integer = Array( "
  resultArr.Append Join( addArr, ", " )
  resultArr.Append " )"
  resultArr.Append eol
  
  resultArr.Append "dim indexArr() as Integer = Array( "
  resultArr.Append Join( indexArr, ", " )
  resultArr.Append " )"
  resultArr.Append eol
  
  resultArr.Append "indexArr.SortWith codeArr, adderArr"
  resultArr.Append eol
  
  resultArr.Append eol
  
  resultArr.Append "dim decodedChars() as String"
  resultArr.Append eol
  
  resultArr.Append "for i as Integer = 0 to codeArr.Ubound"
  resultArr.Append eol
  
  resultArr.Append "decodedChars.Append Chr( codeArr( i ) - adderArr( i ) )"
  resultArr.Append eol
  
  resultArr.Append "next i"
  resultArr.Append eol
  
  resultArr.Append eol
  
  resultArr.Append "dim decodedString as String = Join( decodedChars, """" )"
  resultArr.Append eol
  
  dim result as String = Join( resultArr, "" )
  
  b = ShowDialog( "Copy to clipboard or paste in place?", result, "Copy", "Cancel", "Paste" )
  select case b
  case "Cancel"
    return
  case "Copy"
    Clipboard = result
  case "Paste"
    SelText = result
  end select

That’s so awesome!
I’ve snipped out and made it always paste in place, but I’m saving it as Obfuscate_Kem so I can remember where it came from :smiley:

Thanks <(^.^)>

Wow! That’s absolutely awesome!

I did a little more modifying here…
Use a random multiplier for each character rather than adder.
Use double values randomly incremented for the sort array.
Replace the quoted text with decodedString, and paste the encoding section at the top of the current method.
Added an “End Encoding” comment after the decoding block

[code]
dim origString as String = SelText
if origString.Trim = “” then
print “Select some text first.”
return
end if

dim chars() as String = Split( origString, “” )

dim startQuote as boolean = chars( 0 ) = “”""
dim endQuote as boolean = chars( chars.Ubound ) = “”""

if endQuote then
chars.Remove chars.Ubound
end if

if chars.Ubound <> -1 and startQuote then
chars.Remove 0
end if

if chars.Ubound = -1 then
print “Select some valid text first.”
return
end if

dim stringToEncode as String = Join( chars, “” )
dim b as String = ShowDialog( “You are about to encode this string. Proceed?”, stringToEncode, “Yes”, “No”, “” )
if b = “No” then
return
end if

dim index as Integer
dim codeArr() as String
dim indexArr() as String
dim multArr() as String
dim randomizerArr() as integer
dim lastIndex as double
for index = 0 to chars.Ubound
dim thisMult as integer = (rnd)100
lastIndex=lastIndex+max(1,rnd
10)
codeArr.Append Str( Asc( chars( index ) ) * thisMult )
indexArr.Append Str( lastIndex )
multArr.Append Str( thisMult )
randomizerArr.Append rnd()* chars.Ubound * 100
next index

randomizerArr.SortWith( codeArr, indexArr, multArr )

// Construct the code
dim eol as String = EndOfLine
dim resultArr() as String

resultArr.Append "//Encoding for value: "
resultArr.Append stringToEncode
resultArr.Append eol

resultArr.Append "dim codeArr() as integer = Array( "
resultArr.Append Join( codeArr, “, " )
resultArr.Append " )”
resultArr.Append eol

resultArr.Append "dim multArr() as integer = Array( "
resultArr.Append Join( multArr, “, " )
resultArr.Append " )”
resultArr.Append eol

resultArr.Append "dim indexArr() as double = Array( "
resultArr.Append Join( indexArr, “, " )
resultArr.Append " )”
resultArr.Append eol

resultArr.Append “indexArr.SortWith codeArr, multArr”

resultArr.Append eol

resultArr.Append “dim decodedChars() as String”
resultArr.Append eol

resultArr.Append “for i as Integer = 0 to codeArr.Ubound”
resultArr.Append eol

resultArr.Append “decodedChars.Append Chr( codeArr( i ) / multArr( i ) )”
resultArr.Append eol

resultArr.Append “next i”
resultArr.Append eol

resultArr.Append “dim decodedString as String = Join( decodedChars, “””" )"
resultArr.Append eol

resultArr.Append "//End Encoding for "
resultArr.Append stringToEncode
resultArr.Append eol
resultArr.Append eol

dim result as String = Join( resultArr, “” )

b = ShowDialog( “Copy to clipboard or paste in place?”, result, “Copy”, “Cancel”, “Paste” )
select case b
case “Cancel”
return
case “Copy”
Clipboard = result
case “Paste”
SelText = “decodedString”
selLength = 0
selStart = 0
selText = result
end select[/code]

As Larry Page says, “Strong encryption will always prevail over obfuscation. Together, they are nearly unstoppable.”
:slight_smile:

I think that y’all right here.

I’ll start with Brad, because that’s the easiest to comment on: I agree in principle with. Basically if we asses the situation here. What we’re talking about is prevent someone from looking at the binary in Matt’s ‘Hack’ app (or even a plain old text editor) and discovering serial numbers used for third party code. So let’s look at the main players for third party code.

MBS, includes obfuscation code in the receipt e-mail.

Einhugur uses purchase time decryption, so there isn’t any runtime activation.

eSellerate (someone mentioned them), mainly the code identifies your store and products, so if someone obtained that info, they could sell your products on your store. eSellerate’s a moot point, because unless you do $USD 60,000 a month, they would rather you crawl into a small hole and leave them alone.

Obfuscation might stop a script kiddie from extracting this information via Matt’s tool or a good 'ole text editor, however it won’t stop a more seasoned cracker. Which is Brad’s point. You can spend a lot of time protecting the serial numbers of third party tools, only to have them stolen any way. Bear in mind, the only people who these serial numbers are useful to, are Xojo developers.

At the end of the day, it’s up to you how you allocate your time, it might be better spent in designing & implementing better features (to fend off your competition) than pouring a lot of effort into protecting your application from one kind of basic (ha!) villain.

Now if there was anything we could do to stop them running a debugger and stepping though compiled code, I’m all ears.

Talking of cars, newer cars are now actually easier for script kiddies to steal, thanks to manufacturer overrides. I recently read an article claiming that you can buy a small box about the size of a cigarette packet, that sends manufacturer ‘override’ commands for most major brands. This one box can now unlock the car, but also with push to start ignition will enable the thief to steal the car. No skills required, and it’s only about $5,000 US.

I appreciate the thoughts, but in my case, I will be requesting info via an event and comparing my obfuscated value and proceeding from there. The info never leaves the function where it is generated… I may even do a byte by byte comparison to avoid having the info stored in a string…
That’s safe enough for my purposes for now.
And I’ve put enough time into this… well over an hour! Back to those better features I go! :wink: