如何生成和validation软件许可证密钥?
我目前正在开发一款产品(用C#开发),可以免费下载和安装,但是版本非常有限。 要访问所有function,用户必须支付许可证费用并获得一个密钥。 然后将该密钥input到应用程序中以“解锁”完整版本。
因为使用像这样的许可证密钥是平常我想知道:
- 通常如何解决?
- 我如何生成密钥,以及如何validation应用程序?
- 我怎样才能避免在互联网上发布一个关键字,并被没有支付许可证的其他人使用(一个关键基本上不是他们的)。
我想我也应该以某种方式将应用程序的版本绑定到关键字上,这样才有可能在function版本中为新的关键字收费。
还有什么我应该考虑在这种情况下?
警告:你不能阻止用户盗版,但只能让老实的用户更容易做正确的事情。
假设你不想为每个用户做一个特殊的构build,那么:
- 为您的产品生成一个密钥
- 取用户的名字
- Concatenate用户名和密钥,并与(例如)SHA1散列
- 将SHA1哈希解包为字母数字string。 这是个人用户的“产品密钥”
- 在程序中,做相同的哈希,并与产品密钥进行比较。 如果相等,确定。
但是,我再说一遍: 这不会阻止盗版
我最近读到这种方法不是密码学上非常健全的。 但是这个解决scheme已经很薄弱( 因为软件本身必须包含密钥 ),所以我不认为这个发现会使解决scheme失效。
只是觉得我真的应该提到这一点,虽然; 如果你打算从这个其他的东西,请注意。
有许多方法可以生成许可证密钥,但是很less有这些方法是真正安全的。 很遗憾,因为对于公司来说,许可证密钥的价值几乎与真实现金相同。
理想情况下,您希望您的许可证密钥具有以下属性:
-
只有你的公司应该能够为你的产品生成许可证密钥,即使有人完全反向工程你的产品(这将发生,我从经验讲)。 如果您认真对待授权,则在您的软件中混淆algorithm或隐藏encryption密钥实际上是不可能的。 如果你的产品是成功的,那么有人会在发布后的几天内制造一个关键的产品。
-
许可证密钥只能在一台计算机上使用(或者至less应该能够非常紧密地控制这个密钥)
-
许可证密钥应该很短并且容易通过电话input或口述。 您不希望每个客户都致电技术支持,因为他们不知道密钥是否包含“l”或“1”。 您的支持部门会为此感谢您,并且您在这方面的成本会更低。
那么你如何解决这些挑战呢?
-
答案很简单,但是在技术上却很有挑战性:使用公钥encryption的数字签名。 您的许可证密钥实际上应该是签名的“文档”,其中包含一些有用的数据,并使用贵公司的私钥签名。 签名应该是许可证密钥的一部分。 产品应使用相应的公钥validation许可证密钥。 这样,即使有人可以完全访问您的产品的逻辑,也不能生成许可证密钥,因为它们没有私钥。 许可证密钥如下所示:BASE32(CONCAT(DATA,PRIVATE_KEY_ENCRYPTED(HASH(DATA))))这里最大的挑战是经典公钥algorithm具有较大的签名大小。 RSA512有一个1024位的签名。 您不希望您的许可证密钥有数百个字符。 最有效的方法之一是使用椭圆曲线密码(仔细实施以避免现有专利)。 ECC密钥比RSA密钥短6倍,具有相同的强度。 您可以使用像Schnorr数字签名algorithm(专利在2008年过期 – 好:)等algorithm进一步减less签名大小)
-
这可以通过产品激活来实现(Windows是一个很好的例子)。 基本上,对于拥有有效许可证密钥的客户,您需要生成一些“激活数据”,这是一个签名消息,将计算机的硬件IDembedded到签名数据中。 这通常通过互联网完成,但只有一次:产品将许可证密钥和计算机硬件ID发送到激活服务器,并且激活服务器将签署的消息发回(也可以使签名消息变得简短并容易指定电话)。 从那时起,产品在启动时不检查许可证密钥,而是激活数据,为了validation需要计算机是相同的(否则,数据将不同,数字签名不能validation)。 请注意,激活数据检查不需要通过Internet进行validation:使用已embedded产品中的公钥validation激活数据的数字签名就足够了。
-
那么,只需从您的键中删除多余的字符,如“1”,“l”,“0”,“o”。 将许可证密钥string拆分为多个字符组。
简单的答案 – 不pipe你使用什么scheme都可以被破解。
不要用一个旨在防止黑客的系统惩罚诚实的客户,因为黑客无论如何都会破解它。
一个简单的哈希代码绑定到他们的电子邮件或类似的可能是够好的。 当人们需要重新安装或更新硬件时,基于硬件的ID总是成为问题。
关于这个问题的好主意: http : //discuss.joelonsoftware.com/default.asp?biz.5.82298.34
生成密钥时,不要忘记将版本和内部版本号连接到您计算散列的string。 这样就不会有一把钥匙可以解锁你发布的所有东西。
在astalavista.box.sk中find一些键或补丁之后,你就会知道你已经成功地做出了一些足够stream行的东西,以至于有人打扰了。 麾!
除了已经陈述的….
由于中间语言问题,任何.NET应用程序的使用本质上都是可以破解的。 .NET代码的一个简单反汇编将打开你的产品给任何人。 他们很容易绕过你的授权码。
你甚至不能使用硬件值来创build一个密钥了。 虚拟机现在允许某人创build“许可”机器的图像,并在任何他们select的平台上运行。
如果是昂贵的软件,还有其他解决scheme。 如果不是这样,那么对于偶然的黑客来说就足够困难了。 并接受最终会有无牌拷贝的事实。
如果你的产品很复杂,固有的支持问题将会为你创造一些保护。
我们用于许可证密钥生成的C#/ .NET引擎现在保持为开放源代码:
https://github.com/appsoftware/.NET-Licence-Key-Generator 。
它基于“部分密钥validation”系统,这意味着只有您用来生成密钥的密钥的一个子集必须编译到您的可分配中。 您自己创build密钥,因此许可证实施对于您的软件是唯一的。
如上所述,如果您的代码可以反编译,那么避开大多数许可系统是相对容易的。
我以前用过Crypkey 。 这是许多可用的之一。
您只能使用任何授权计划来保护软件。
我不知道你想得到多么详尽
但我相信.net可以访问硬盘序列号。
你可以让程序发送给你,还有一些东西(比如nic的用户名和mac地址)
你计算一个基于此的代码,并通过电子邮件发回密钥。
他们有钥匙后不让他们换机器。
要求你做的所有事情的唯一方法是要求互联网访问和服务器validation。 应用程序需要使用密钥login到服务器,然后您需要存储会话详细信息,如IP地址。 这将防止在几台不同的机器上使用密钥。 这通常不是应用程序用户非常喜欢的,除非这是一个非常昂贵和复杂的应用程序,否则不值得。
您可以为应用程序拥有一个许可证密钥,然后在客户端检查密钥是否正常,但是很容易将该密钥分发给其他用户,并且使用反编译器可以生成新的密钥。
我在我公司的软件(C#.net)上实现了基于Internet的一次性激活,它需要一个许可证密钥来引用存储在服务器数据库中的许可证。 软件使用密钥访问服务器,并获得许可证信息,然后使用从客户端计算机上的某些variables(CPUID和其他不会经常变化的组合)生成的RSA密钥在本地进行encryption,然后将其存储在本地registry。
它需要一些服务器端编码,但是它对我们来说工作得非常好,当我们扩展到基于浏览器的软件时,我能够使用相同的系统。 它还为您的销售人员提供关于软件使用的人员,地点和时间的详细信息。 任何只能在本地处理的许可证制度完全容易受到剥削, 特别是在.NET中进行反思 。 但是,正如其他人所说,没有一个制度是完全安全的。
在我看来,如果你不使用基于networking的许可,根本没有真正的保护软件的意义。 由于DRM可能导致的头痛,对于实际付费的用户来说是不公平的。
我坚信,只有基于公钥密码系统的许可证系统才是正确的方法,因为您不必在源代码中包含生成许可证所需的基本信息。
在过去,我多次使用Treek的许可证库 ,因为它满足了这个要求,并且提供了非常好的价格。 它对最终用户和自身使用相同的许可证保护,直到现在还没有人破解。 您也可以在网站上find好的提示,以避免盗版和破解。
完全防止软件盗版是不可能的。 你可以防止盗版,这就是所有的许可解决scheme。
节点(机器)locking许可证是最好的,如果你想防止许可证密钥的重用。 我一直在使用Cryptlex一年左右的软件。 它也有一个免费的计划 ,所以如果你不期望太多的客户,你可以免费使用它。
就像其他人提到的那样,我是违反客户的巨大反对者 – 这是许可行业臭名昭着的事情。 因此,我将针对您的问题展开一个很好的解决scheme, 并提供一个良好的客户用户体验 。
首先,您提到您有一个“有限”版本的软件,用于尝试转换客户以“升级”其他function。 因此,您要查找的是产品的function许可证 ,例如,客户可以购买function-X或function-Y的许可证。
考虑到这种types的许可,我build立了Keygen 。 Keygen是一个许可REST API,允许您pipe理用户帐户,许可证以及跟踪机器使用/关联。
我要做的是设置两个许可证types (Keygen中的一个策略 ),其中一个是有限免费版本的基本策略,另一个是付费版本的策略。
我不知道你用什么付款,但是假设你正在使用像Stripe(现在很标准的)提供webhooks的东西 。 Keygen也有webhooks(无论你使用或不使用,所有这些仍然适用)。 您可以整合Keygen与您的支付提供商使用来自双方的webhook(请考虑: customer.created
– >为客户创build基础许可, license.created
– >向新客户收取新许可)。
所以通过利用webhooks,我们可以自动为新客户创build许可证。 那么应用程序本身的许可证validation呢? 这可以通过多种方式完成,但最stream行的方法是要求客户在input字段中input长许可证密钥,然后才能validation; 我认为这是在您的应用程序中处理许可证validation的可怕方法。
我为什么这么想? 那么首先,你要求你的客户input一个冗长的许可证密钥,这个密钥是用于机器消耗的;其次, 你要求你和你的客户跟踪那个冗长的许可证密钥 。
好的,有什么select? 我认为最好的select是做所有客户习惯的事情: 允许他们使用电子邮件/密码为您的产品创build一个帐户 。 然后,您可以将其所有许可证及其机器与该帐户相关联。 因此,现在不用input许可证密钥,只需使用凭据login即可。
这给你什么好处? 首先,它不需要您和您的客户来跟踪许可证密钥, 因为它们都是在用户帐户的幕后处理的 ,最重要的是: 您现在可以为您的客户提供自助服务许可证和机器激活! 即由于所有的许可证和机器都与其用户帐户相关联,所以当他们在无法识别的机器上启动应用程序时,可以提示他们购买许可证。
现在进行许可证validation :只要您的客户使用他们的电子邮件/密码login到您的应用程序,就可以查询他们的用户帐户以获取他们拥有的许可证,以确定他们是否可以使用feature-X或feature-Y 。 而且由于您的应用程序现在可以自助服务 ,您可以让您的客户直接从应用程序内购买其他function!
所以我们为我们的授权系统引入了大量的自动化function,我们可以授权个人function (即有限制版本和完整版本),我们为客户提供了一个很棒的用户体验,同时也缓解了其中一个最大的原因用于支持请求: 许可证密钥恢复。
无论如何,这有很长的一段时间,但希望它可以帮助别人!