1

I have made an PC app in visual studio 2017 .net c# and compiled it to an exe. And then I thought my code was safe and nobody could see it because it was compiled, but when I open the exe in a program like .net reflector I can see the source code.

Is there any way I can prevent that? Or protect me against Decompiling??

  • The only way to stay safe is to perform online validation and store important resources online. There is no real way to protect an offline application. If computer knows how to run it, programmers will too. – FCin Aug 06 '17 at 09:14
  • What are your security requirements? can you give some more details? – ironstone13 Aug 06 '17 at 09:16
  • My program needs to generate and store a fingerprint of the computer. And it would be great if the user couldn't see how the fingerprint was generated. Plus when I stored the fingerprint I encrypted it first, but that doesn't work if the user just can look at the source code and get the encryption password. So I think im just gonna drop the encryption of the fingerprint. – Kasper Tonsgaard Aug 06 '17 at 09:25
  • Why not do the calculation of the fingerprint on the server side? Just encrypt all the necessary data and send it to the server, that is hosted in a secure environment. Client code does not have to know that at all - it looks like you're design is off a bit – ironstone13 Aug 06 '17 at 09:30
  • My fingerprint consists of some hardware serials. Do you want me to send them to the server secure (https?) And then the server generates the fingerprint and sends it back to the client/program?? – Kasper Tonsgaard Aug 06 '17 at 09:42
  • 1
    If you send them *back* then the client program has to *store* it somewhere, perhaps in an encrypted manner. You could also instead store it on the server, in a place that is not accessible by the user. In such a case you would need to send encrypted hardware serials to the server each time, compute and compare to what you have stored. This is not very performant, but more secure. It all depends on your requirements – ironstone13 Aug 06 '17 at 09:45
  • The fingerprint is used to identify each computer in the database – Kasper Tonsgaard Aug 06 '17 at 09:49

2 Answers2

4

There's really no point in attempting this.

While you'll be inundated with "obfuscation", this is a poor waste of time.

  • Deobfuscators are getting better all the time.
  • If someone wants your code bad enough they'll get it no matter what you do.
  • Frankly, if you are asking this question then the code you wrote isn't worth the time it would take to protect it.
Sam Axe
  • 33,313
  • 9
  • 55
  • 89
  • The harsh truth, but what about Ngen.exe and generating native images? (And taking all the trouble for doing that) – ironstone13 Aug 06 '17 at 09:14
  • 1
    @ironstone13: There's better languages for writing native images. And good arguments for using them. But even those can be decompiled. I understand the argument for code protection.. but the current state of the tools make the effort of that protection very expensive - in terms of time, ease of workflow, and ease of maintenance. – Sam Axe Aug 06 '17 at 09:18
  • So I can go download any .net application that is not full version and copy the source code remove some code so it think it is the full version and then recompile the program as nothing happened?? – Kasper Tonsgaard Aug 06 '17 at 09:29
  • @KasperTonsgaard - well it depends on what do you mean by *nothing happened*. If you are implying that you can **substitute** the assembly, then you can be safe from that by using strong named assemblies - see https://learn.microsoft.com/en-us/dotnet/framework/app-domains/strong-named-assemblies – ironstone13 Aug 06 '17 at 09:35
  • Don't understand it. What does it?? – Kasper Tonsgaard Aug 06 '17 at 09:39
  • @KasperTonsgaard, basically it guarantees that an assembly in your application cannot be replaced seamlessly by some other assembly, that could be altered by someone else. – ironstone13 Aug 06 '17 at 09:47
  • 2
    @ironstone13 No, it doesn't help for that. By design, the local system administrator can disable strong name verification for specific keys. This is used by Entity Framework for instance to build with the official Microsoft public key, not provide the private key to sign the assembly, yet still allow local use of the custom-built version. –  Aug 06 '17 at 09:50
  • 2
    @ironstone13 Probably more relevant though is that if it's an *application* rather than just an assembly, the user can just replace it with an unsigned version, or a version signed with some other key. –  Aug 06 '17 at 09:51
  • @KasperTonsgaard, you may implement your confidential code in a C++/CLI assembly (unmanaged C++ for confidential things). That makes it much more complicated to decompile and understand that code. And if you use a secure hash algorithm, e.g. SHA256, for the fingerprint, that might be secure enough for ~99% of the users. – KBO Aug 07 '17 at 11:21
  • 1
    @ironstone13 nothing prevents people from reverse engineering a native image. Hackers, crackers, antivirus writers, OS developers... do that all the time – phuclv Apr 06 '20 at 14:11
  • @phuclv - yes, of course - you are right. With native images, reverse engineering is just much more difficult, and thus, reverse engineering the whole code base (say, of a large enterprise application) is impractical, so the focus shifts to a smaller part that can be hacked – ironstone13 Apr 06 '20 at 19:07
1

You cannot prevent decompiling, if you compile into MSIL (intermediate language). In such case you need to use obfuscation

For a deeper discussion on the subject check out this post .NET obfuscation tools/strategy

You can find a similar discussion here How can I obfuscate my c# code, so it can't be deobfuscated so easily?

You can also opt to generate a native image using Ngen.exe for a specific platform - that will bypass the IL and generate compiled processor specific machine code, and that one is pretty much safe from standpoint of reverse - engineering.

Using an IL is a quite common design choice - and it has it's drawbacks and benefits - the main ones being easier support of multiple languages on one platform, and multiple target platforms, i.e cross platform

To get a glimpse of some of the benefits of using IL - check this out - stackoverflow.com/questions/1926386/…

Java also uses an intermediate language - java bytecode - javaworld.com/article/2077233/core-java/bytecode-basics.html

ironstone13
  • 3,325
  • 18
  • 24
  • 1
    But I had a c++ program and I couldn't get the source code of that. Why not?? – Kasper Tonsgaard Aug 06 '17 at 09:14
  • @KasperTonsgaard, that is **exactly the point** - if the C++ program did not run on .NET, then it does not use IL and is not so vulnerable to reverse engineering - see https://stackoverflow.com/questions/8710581/what-is-the-main-difference-between-c-vs-c-net – ironstone13 Aug 06 '17 at 09:18
  • But why can't Microsoft just make .net so you can't read the source code?? – Kasper Tonsgaard Aug 06 '17 at 09:20
  • 1
    It's a quite common design choice I'm afraid - and it has it's drawbacks and benefits - the main ones being easier support of multiple languages on one platform, and multiple target platforms To get a glimpse of some of the benefits of using IL - check this out - https://stackoverflow.com/questions/1926386/why-net-code-compiles-to-msil Java also uses an intermediate language - java bytecode - http://www.javaworld.com/article/2077233/core-java/bytecode-basics.html – ironstone13 Aug 06 '17 at 09:29
  • @KasperTonsgaard who said that you can't get the source code of C++ programs? Haven't you heard of decompilers? And if the CPU can do something, reverse engineer men can also do that. It just takes more time than a language that compiles to byte code like C# or Java – phuclv Apr 06 '20 at 14:10