Android密钥证书管理相关介绍

2023-05-16

Java Security
Java Security是Java中的安全模块,它对应了一系列的规范,主要包含三个重要规范:
JavaCryptography Extension(简写为JCE),JCE所包含的内容有加解密,密钥交换,消息摘要(Message Digest,比如MD5等),密钥管理等。
JavaSecure Socket Extension(简写为JSSE),JSSE所包含的内容就是Java层的SSL/TLS。简单点说,使用JSSE就可以创建SSL/TLS socket了。
JavaAuthentication and Authorization Service(简写为JAAS),JSSA和认证/授权有关。这部分内容在客户端接触得会比较少。

JCE设计架构
JCE在设计时重点关注两个问题:其功能具体实现的独立性和可互操作性;使用算法的独立性和可扩展性。
对于独立性而言,一个最通用的做法就是把定义和实现通过抽象类或基类的方式进行解耦合。
在JCE中:它首先把功能组合成一个一个的Service(也称作Engine)。比如,对应“加解密”的API组合成CipherService,对应“消息摘要”的API组合成MessageDigest Service,对应“签名”的API组合成SignatureService。JCE为这些Service都定义了一个诸如XXXSpi的抽象类。其中,SPI是Service Provider Interface的缩写。
上述SPI的具体实现则由不同的Provider来提供。比如JDK会提供一组默认的实现(当然,这些实现以前是由Sun公司,现在由Oracle提供。注意,Provider可以提供一组Service的实现,也可以提供单个Service的实现。

Android Security
继承自Java Security
Service Provider:“原版”的 Java 版本中,Service Provider 多数是 Sun 和 IBM 的作品,而 Android 选用了3个开源项目的代码:Harmony、Bouncy Castle、OpenSSL。
Harmony:是一个比较复杂的 Java 项目,Android 只用了其中 Security、xnet 的一部分代码,其 Provider 仅提供 SSL/TLS 的支持,另外的部分代码用于 X.509 数字证书对象的解释等等。Harmony 的代码已多年没有更新了,所以 Android 的这部分代码也一直没有变动,4.0 之后,增加了一个“AndroidCAStore”还是挺实用的。
Bouncy Castle:是 Android 中功能最丰富的 Service Provider,没有之一(但不提供 SSL/TLS 的直接支持),而且 Android 版本的升级同时也采用当时最新的 Bouncy Castle 版本的代码。早期的 Android 版本沿用 Bouncy Castle 的包名前缀 org.bouncycastle.,从 3.0 开始,包名前缀改为 com.android.org.bouncycastle.,这样的改动不影响 JCE 的兼容性,却为应用软件开发者采用“原版”的 Bouncy Castle 提供了方便。
OpenSSL:是 C 语言编写的著名开源项目,Android 通过 JNI 将其封装为一个 “AndroidOpenSSL”,早期的版本仅用于对 WebView 提供 https 支持(而且是仅用于单向 SSL),后来逐渐丰富,到了 4.2,已支持大多数常用的加密算法,4.4之后则更为丰富,大有取代 Bouncy Castle 的势头。
从 4.2 开始,Android 新增了一个 Service Provider,命名为 AndroidKeyStore,此前,在 Android 中的 KeyStore 只有 bks 和 PKCS#12 两种格式,底层由 Bouncy Castle 的代码来实现,而 AndroidKeyStore 的底层则因 Android 版本的不同而差别很大,在应用层来看,AndroidKeyStore 可看作是 JCE 的 KeyStore 中的一种,但其 load 方法中所有参数都须为 null,而且没有 store 方法。

KeyStore服务
对于公开的加密算法而言,其实际应用的安全性主要取决于加密密钥的安全;一旦密钥被获取,信息就会被破解窃取。为有效保护加密密钥, Android特设了一套密钥管理机制,即KeyStore密钥库。
KeyStore为应用提供了生成与获取密钥或者证书的服务,是一个原生的后台守护进程。最开始Android使用本地Socket作为其与客户端沟通的方式。从4.3开始,经过重新设计,现在Keystore使用Binder代替本地Socket来实现进程间通信。这种方式更加符合目前Android中Framework下各项服务的设计规范,同时也有利于其将来的功能扩展。

KeyStore启动
Android启动过程中由init进程解析rc获取启动keystore服务的相关信息。
system/security/keystore/keystore.rc
service keystore /system/bin/keystore /data/misc/keystore
class main
user keystore
group keystore drmrpc readproc
writepid /dev/cpuset/foreground/tasks
keystore属于main类服务,因此当init执行到start_class main时,也就会自动加载keystore服务。启动时将会以keystore的UID运行,其所保存的数据信息将会存放在/data/misc/keystore目录下。在这个目录下我们可以看到各个手机用户(目前一般只有一个用户user_0)所拥有的各项证书。其中各项数据的名称包含有对应应用的UID,证书类型,以及证书别名。由于有UID作为前缀,因此,应用在保存证书时只要保证该别名在应用内部的唯一性即可。
system/security/keystore/keystore_main.cpp
keymaster_device_initialize(&dev)
chdir -> /data/misc/keystore

KeyStore API:
test 检测密钥是否可用
get 按名称查找密钥并返回
insert 保存一个密钥,如果有同名的覆盖
del 删除给定名称的密钥
exist 检测给定名称的密钥是否存在
saw 列出当前所能访问的密钥
reset 清空密钥保存区
password 修改KeyStore的密码
lock 锁定KeyStore
unlock 解锁KeyStore
zero 检测KeyStore中是否为空

KeyStore使用
Android上的Keystore目前主要分为两类分别是BKS和AndroidKeyStore。 BKS是一个对Java中的加密库Bouncy Castle精简后的版本,其剔除了一些向创建证书等开发者为很少在Android上使用的功能。而如果应用中需要使用到相关功能时也可以自行导入完整的BouncyCastle,为防止名称冲突其在Android中称之为Spongy Castle。一般BKS将密钥存储在文件中。 AndroidKeyStore是从Android4.3开始引入进来的。可以通过 KeyStore. getInstance (“AndroidKeyStore”)或KeyPairGenerator.getInstance(algorithm, provider)来使用。开发者通过他可以自己创建与管理只属于该应用自身的密钥,目前公开的API只允许使用非对称加密算法的密钥与证书。

KeyChain
从4.0(API 14)开始Android引入了一个新的类android.security.KeyChain。该类向外界提供了一个能够访问和存储系统范围内全局证书的接口。在这之前,这些证书只有系统级的WIFI和VPN等少数应用可以访问。该类为BYOD(Bring Your Own Device)之类的服务提供了很大的便利,使得PKI等技术可以方便的应用在Android系统之上。Android同时还提供了一套UI,第三方应用要访问证书时,会自动调用该UI来让用户来选择是否允许以及具体访问哪一个证书。

KeyChain API:
frameworks/base/keystore/java/android/security/IKeyChainService.aidl
// APIs used by KeyChain
String requestPrivateKey(String alias); 该方法通过参数alias来返回对应的私钥。

byte[] getCertificate(String alias); 该方法通过参数alias来返回对应的证书。

// APIs used by CertInstaller
void installCaCertificate(in byte[] caCertificate); 用户安装新的证书,通过该Intent,系统将会该处一个UI,让用户为导入的证书选取别名(alias),以后应用可以通过该别名索引到该证书。

// APIs used by DevicePolicyManager
boolean installKeyPair(in byte[] privateKey, in byte[] userCert, String alias);

// APIs used by Settings
boolean deleteCaCertificate(String alias);
boolean reset();
ParceledListSlice getUserCaAliases();
ParceledListSlice getSystemCaAliases();
boolean containsCaAlias(String alias);
byte[] getEncodedCaCertificate(String alias, boolean includeDeletedSystem);
List getCaCertificateChainAliases(String rootAlias, boolean includeDeletedSystem);

// APIs used by KeyChainActivity
void setGrant(int uid, String alias, boolean value);
boolean hasGrant(int uid, String alias);

KeyMaster
以前keystore服务将密钥管理与加密服务通过一个软件来实现,自4.1开始Android引入一个新的HAL(hardware abstraction layer)模块keymaster,其专门负责创建非对称密钥,同时还可以在其内部完成数据的签名与验证工作,这样省去了将密钥导出给外部的过程从而加强了密钥的安全性。 keymaster的引入不仅减轻了keystore的任务同时也方便了后续引入硬件级的密钥存储,与硬件加密模块。对于不支持硬件加密与硬件存储密钥的设备,Android加入一个softkeymaster的模块来通过软件的方式使用OpenSSL的库处理相应的密钥操作。Android Kitkat之前密钥使用的是RSA的2048bit的密钥,Kitkat开始支持DSA(Digital Signature Algorithm)和ECDSA(Elliptic Curve DSA)密钥且大小可自己指定。
目前keymaster支持的操作有:generate_keypair, import_keypair, sign_data, verify_data, get_keypair_public, delete_keypair, delete_all。

密钥存储类型:
可通过“设置->安全->凭证存储->存储类型”查看。
packages/apps/Settings/src/com/android/settings/SecuritySettings.java
final int storageSummaryRes = keyStore.isHardwareBacked() ?
R.string.credential_storage_type_hardware :
R.string.credential_storage_type_software;

证书
从版本 1.6 开始通过“设置->安全->凭据存储->从SD卡安装”操作,可以将SD卡根目录下的证书文件(.cer, .crt, .p12, .pfx)安装到系统的“凭证库”里。凭证库分为“受信任的凭证”和“用户凭证”两部分,安装时根据文件内容会自动决定安装在哪里,凭证库里证书及其私钥用于浏览器(WebView)、VPN 以及 Wi-Fi WAPI 设备的认证,如果你编写的 App 仅需要 https 通信来保障数据安全,则几乎不需要在代码上操心,只须指导用户去获取并安装证书就好了。从 4.0 开始,Android 提供了一组 API 使应用程序也能访问这个库:android.security.KeyChain。

受信任的凭证
可通过“设置->安全->凭证存储->受信任的凭证”查看。
libcore/luni/src/main/files/cacerts/该目录下预置了一百多个系统CA证书。
示例:libcore/luni/src/main/files/cacerts/ff783690.0
内容如下:
—–BEGIN CERTIFICATE—–
MIIEdDCCA1ygAwIBAgIQRL4Mi1AAJLQR0zYq/mUK/TANBgkqhkiG9w0BAQUFADCB
lzELMAkGA1UEBhMCVVMxCzAJBgNVBAgTAlVUMRcwFQYDVQQHEw5TYWx0IExha2Ug
Q2l0eTEeMBwGA1UEChMVVGhlIFVTRVJUUlVTVCBOZXR3b3JrMSEwHwYDVQQLExho
dHRwOi8vd3d3LnVzZXJ0cnVzdC5jb20xHzAdBgNVBAMTFlVUTi1VU0VSRmlyc3Qt
SGFyZHdhcmUwHhcNOTkwNzA5MTgxMDQyWhcNMTkwNzA5MTgxOTIyWjCBlzELMAkG
A1UEBhMCVVMxCzAJBgNVBAgTAlVUMRcwFQYDVQQHEw5TYWx0IExha2UgQ2l0eTEe
MBwGA1UEChMVVGhlIFVTRVJUUlVTVCBOZXR3b3JrMSEwHwYDVQQLExhodHRwOi8v
d3d3LnVzZXJ0cnVzdC5jb20xHzAdBgNVBAMTFlVUTi1VU0VSRmlyc3QtSGFyZHdh
cmUwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCx98M4P7Sof885glFn
0G2f0v9Y8+efK+wNiVSZuTiZFvfgIXlIwrthdBKWHTxqctU8EGc6Oe0rE81m65UJ
M6Rsl7HoxuzBdXmcRl6Nq9Bq/bkqVRcQVLMZ8Jr28bFdtqdt++BxF2uiiPsA3/4a
MXcMmgF6sTLjKwEHOG7DpV4jvEWbe1DByTCP2+UretNb+zNAHqDVmBe8i4fDidNd
oI6yqqr2jmmIBsX6iSHzCJ1pLgkzmykNRg+MzEk0sGlRvfkGzWitZky8PqxhvQqI
DsjfPe58BEydCl5rkdbux+0ojatNh4lz0G6k0B4WixThdkQDf2Os5M1JnMWS9Ksy
oUhbAgMBAAGjgbkwgbYwCwYDVR0PBAQDAgHGMA8GA1UdEwEB/wQFMAMBAf8wHQYD
VR0OBBYEFKFyXyYbKJhDlV0HN9WFlp1L0sNFMEQGA1UdHwQ9MDswOaA3oDWGM2h0
dHA6Ly9jcmwudXNlcnRydXN0LmNvbS9VVE4tVVNFUkZpcnN0LUhhcmR3YXJlLmNy
bDAxBgNVHSUEKjAoBggrBgEFBQcDAQYIKwYBBQUHAwUGCCsGAQUFBwMGBggrBgEF
BQcDBzANBgkqhkiG9w0BAQUFAAOCAQEARxkP3nTGmZev/K0oXnWO6y1n7k57K9cM
//bey1WiCuFMVGWTYGufEpytXoMs61quwOQt9ABjHbjAbPLPSbtNk28Gpgoiskli
CE7/yMgUsogWXecB5BKV5UU0s4tpvc+0hY91UZ59Ojg6FEgSxvunOxqNDYJAB+gE
CJChicsZUN/KHAG8HQQZexB2lzvukJDKxA4fFm517zP4029bHpbj4HR3dHuKom4t
3XbWOTCC8KucUvIqx69JXn7HaOWCgchqJ/kniCrVWFCVH/A7HFe7fRQ5YiuayZSS
KqMiDP+JJn1fIytH1xUdqWqeUQ0qUZ6B+dQ7XnASfxAynB67nfhmqA==
—–END CERTIFICATE—–
Certificate:
Data:
Version: 3 (0x2)
Serial Number:
44:be:0c:8b:50:00:24:b4:11:d3:36:2a:fe:65:0a:fd
Signature Algorithm: sha1WithRSAEncryption
Issuer: C=US, ST=UT, L=Salt Lake City, O=The USERTRUST Network, OU=http://www.usertrust.com, CN=UTN-USERFirst-Hardware
Validity
Not Before: Jul 9 18:10:42 1999 GMT
Not After : Jul 9 18:19:22 2019 GMT
Subject: C=US, ST=UT, L=Salt Lake City, O=The USERTRUST Network, OU=http://www.usertrust.com, CN=UTN-USERFirst-Hardware
Subject Public Key Info:
Public Key Algorithm: rsaEncryption
Public-Key: (2048 bit)
Modulus:
00:b1:f7:c3:38:3f:b4:a8:7f:cf:39:82:51:67:d0:
6d:9f:d2:ff:58:f3:e7:9f:2b:ec:0d:89:54:99:b9:
38:99:16:f7:e0:21:79:48:c2:bb:61:74:12:96:1d:
3c:6a:72:d5:3c:10:67:3a:39:ed:2b:13:cd:66:eb:
95:09:33:a4:6c:97:b1:e8:c6:ec:c1:75:79:9c:46:
5e:8d:ab:d0:6a:fd:b9:2a:55:17:10:54:b3:19:f0:
9a:f6:f1:b1:5d:b6:a7:6d:fb:e0:71:17:6b:a2:88:
fb:00:df:fe:1a:31:77:0c:9a:01:7a:b1:32:e3:2b:
01:07:38:6e:c3:a5:5e:23:bc:45:9b:7b:50:c1:c9:
30:8f:db:e5:2b:7a:d3:5b:fb:33:40:1e:a0:d5:98:
17:bc:8b:87:c3:89:d3:5d:a0:8e:b2:aa:aa:f6:8e:
69:88:06:c5:fa:89:21:f3:08:9d:69:2e:09:33:9b:
29:0d:46:0f:8c:cc:49:34:b0:69:51:bd:f9:06:cd:
68:ad:66:4c:bc:3e:ac:61:bd:0a:88:0e:c8:df:3d:
ee:7c:04:4c:9d:0a:5e:6b:91:d6:ee:c7:ed:28:8d:
ab:4d:87:89:73:d0:6e:a4:d0:1e:16:8b:14:e1:76:
44:03:7f:63:ac:e4:cd:49:9c:c5:92:f4:ab:32:a1:
48:5b
Exponent: 65537 (0x10001)
X509v3 extensions:
X509v3 Key Usage:
Digital Signature, Non Repudiation, Certificate Sign, CRL Sign
X509v3 Basic Constraints: critical
CA:TRUE
X509v3 Subject Key Identifier:
A1:72:5F:26:1B:28:98:43:95:5D:07:37:D5:85:96:9D:4B:D2:C3:45
X509v3 CRL Distribution Points:

            Full Name:
              URI:http://crl.usertrust.com/UTN-USERFirst-Hardware.crl

        X509v3 Extended Key Usage: 
            TLS Web Server Authentication, IPSec End System, IPSec Tunnel, IPSec User
Signature Algorithm: sha1WithRSAEncryption
     47:19:0f:de:74:c6:99:97:af:fc:ad:28:5e:75:8e:eb:2d:67:
     ee:4e:7b:2b:d7:0c:ff:f6:de:cb:55:a2:0a:e1:4c:54:65:93:
     60:6b:9f:12:9c:ad:5e:83:2c:eb:5a:ae:c0:e4:2d:f4:00:63:
     1d:b8:c0:6c:f2:cf:49:bb:4d:93:6f:06:a6:0a:22:b2:49:62:
     08:4e:ff:c8:c8:14:b2:88:16:5d:e7:01:e4:12:95:e5:45:34:
     b3:8b:69:bd:cf:b4:85:8f:75:51:9e:7d:3a:38:3a:14:48:12:
     c6:fb:a7:3b:1a:8d:0d:82:40:07:e8:04:08:90:a1:89:cb:19:
     50:df:ca:1c:01:bc:1d:04:19:7b:10:76:97:3b:ee:90:90:ca:
     c4:0e:1f:16:6e:75:ef:33:f8:d3:6f:5b:1e:96:e3:e0:74:77:
     74:7b:8a:a2:6e:2d:dd:76:d6:39:30:82:f0:ab:9c:52:f2:2a:
     c7:af:49:5e:7e:c7:68:e5:82:81:c8:6a:27:f9:27:88:2a:d5:
     58:50:95:1f:f0:3b:1c:57:bb:7d:14:39:62:2b:9a:c9:94:92:
     2a:a3:22:0c:ff:89:26:7d:5f:23:2b:47:d7:15:1d:a9:6a:9e:
     51:0d:2a:51:9e:81:f9:d4:3b:5e:70:12:7f:10:32:9c:1e:bb:
     9d:f8:66:a8

SHA1 Fingerprint=04:83:ED:33:99:AC:36:08:05:87:22:ED:BC:5E:46:00:E3:BE:F9:D7

这个证书是pem格式,Certificate以下都是明文部分;—–BEGIN CERTIFICATE—–和—–END CERTIFICATE—–之间是编码信息,即将证书的明文内容用Base64编码后得到的字符串。

证书安装路径:
用户证书安装后会被安装到目录/data/misc/keystore/user_0下。
证书权限管理:
程序访问证书是有权限管控的,由KeyChain负责管理,提供的两个主要API是setGrant和hasGrant。权限管理数据库是/data/data/com.android.keychain/databases/grants.db,里面是授权的应用列表,形式为:alias name|app uid。比如,请求私钥的接口requestPrivateKey,如果没有授权的话,返回值将会为null,即使证书安装成功也不能调用到数据。

BKS证书生成与导入
Android 系统中使用的证书要求以BKS的库文件结构保存,这就需要BC库:bcprov-jdk15on-157.jar
下载地址:
https://www.bouncycastle.org/latest_releases.html
下载后将它放置到jdk\jre\lib\ext目录下。
创建密钥证书格式如下:
keytool -genkey -alias <别名> -keypass <密钥口令> -keyalg RSA -keysize 2048 -validity 20000 -keystore <库文件名,如example.keystore> -storepass <证书库密码> -dname “cn=runtestuser3, ou=vpn, o=run, c=CN, l=shanghai” -storetype BKS -provider org.bouncycastle.jce.provider.BouncyCastleProvider
示例如下:
keytool -genkey -alias zzzcacert -keypass 111111 -keyalg RSA -keysize 2048 -validity 20000 -keystore zzzcacert.keystore -storepass 111111 -dname “cn=runtestuser3, ou=vpn, o=run, c=CN, l=shanghai” -storetype BKS -provider org.bouncycastle.jce.provider.BouncyCastleProvider

检查证书:
keytool -list -v -keystore zzzcacert.keystore
-storetype BKS -provider org.bouncycastle.jce.provider.BouncyCastleProvider

导出证书:
keytool -export -alias zzzcacert -file zzzcacert.crt -keystore zzzcacert.keystore -storetype BKS -provider org.bouncycastle.jce.provider.BouncyCastleProvider

导入手机并安装:
1. adb push指令推送文件到内部存储根目录;
2. 点击“设置->安全->凭据存储->从SD卡安装”自动安装内部存储根目录下的证书;或者 进入文件管理器双击证书文件;

安装证书前,查看:

安装证书后,查看:

参考:
Android 数据加密及安全网络通信杂谈(一)
http://blog.csdn.net/suntongo/article/details/51332681?locationNum=3&fps=1
深入理解Android之Java Security第一部分
http://blog.csdn.net/innost/article/details/44081147
深入理解Android之Java Security第二部分(Final)
http://blog.csdn.net/innost/article/details/44199503

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Android密钥证书管理相关介绍 的相关文章

  • hdu1076

    题目链接 An Easy Task 解题思路 题目要求给出一个年份Y和一个整数N xff0c 输入从Y年起第N个闰年 首先我们容易知道我们需要判断一个年份是否是闰年 xff0c 我们可以把它封装成一个函数 xff0c 这样可以方便我们下次调
  • 牛客练习赛12 B迷宫解题报告

    一切尽在代码中 include lt stdio h gt include lt string h gt include lt queue gt include lt algorithm gt using namespace std con
  • 利用并查集维护两个对立集合

    在并查集的实际应用中 xff0c 我们经常遇到下列这种情况的题目 当满足 1 x xff0c y为不同集合的元素 2 x xff0c z为不同集合元素 时 xff0c y xff0c z为相同集合的元素 如何来描述这种不同集合元素的关系就是
  • HDU - 3018解题报告

    题意简述 给出n个节点 xff0c m条边 xff0c 问要想全部经过这m条边且每个边只经过一次至少需要多少条路径 分析 这个题实际上就是一笔画问题中的定理二 xff1a 如果连通无向图 G 有 2k 个奇顶点 xff0c 那么它可以用 k
  • 手把手教你申请企鹅号

    引论 随着互联网时代的兴起 xff0c 自媒体越来越引人注目 笔者周围已经有了不少人开始做自媒体而且还做的顺风顺水 笔者也有些按捺不住 xff0c 寻思着要做自媒体的生意 xff0c 可是转念一想 xff0c 独赚钱不如众赚钱 xff0c
  • UVA818解题报告

    span class hljs comment UVA 818 理解了题意和水题差不多 条件 xff1a 一些可能相同的无向边 要求 xff1a 构建一个满足如下三个要求的图 一 不能有环 二 连成一条直线 三 所有节点要连在一起 操作 x
  • PAT1003 Emergency (25)

    引论 本以为这是一道水题却因为考虑不周WA了半天 xff0c 参考了博客https blog csdn net tiantangrenjian article details 19434417 感觉这题还是蛮不错的 题目链接 https p
  • 操作系统知识点整理

    1 进程的有哪几种状态 xff0c 状态转换图 xff0c 及导致转换的事件 进程的状态 xff1a 运行 阻塞 就绪三种状态 运行和就绪之间的转换由调度程序引导 xff1b 当进程等待一个外部事件发生时 xff0c 则由执行 阻塞 xff
  • uva417

    挺有意思的一道题 迭代深搜 43 二分 实际上根据笔者测试 xff0c 使用迭代深搜打表后直接用暴力枚举也可以通过 xff0c 但如果测试用例T的范围开到1e5在极端情况下就会TLE xff0c 但是UVA的测试数据显然没有这样的 xff0
  • hiho一下 第216周

    分析 这道题挺不错的 xff0c 巧妙的运用到了优先队列 首先 xff0c 因为n个点是确定的 xff0c 所以我们可以得到n 1个区间 xff1b 其次 xff0c 因为还有k个点是不确定的 xff0c 所以我们把这k个点依次插入到这n
  • Cisco packet tracer模拟器基本配置命令

    引言 计算机网络是门实践性很强的学科 xff0c 如果不自己动手做一些实验的话是根本学不好的 我这里的学好是指真正掌握计算机网络的工作原理以及一些常见的网络设备的使用方法 xff0c 而不是期末考高分或者水过一个什么证书 但是通常情况下我们
  • Wannafly挑战赛24A题

    span class hljs comment 题目链接 xff1a https www nowcoder com acm contest 186 A 分析 xff1a 奇数x分为 xff08 1 xff0c x 1 xff09 时为最优解
  • @ControllerAdvice注解作用及源码解析

    一 概述 在Spring里 xff0c 我们可以使用 64 ControllerAdvice来声明一些全局性的东西 xff0c 其用法主要有以下三点 xff1a 1 64 ExceptionHandler注解标注的方法 xff1a 用于捕获
  • 用Android的Activity生命周期解释HarmonyOS的Page Ability生命周期

    由华为出品 我国完全自主知识产权的HarmonyOS是一款 面向未来 面向全场景 xff08 移动办公 运动健康 社交通信 媒体娱乐等 xff09 的分布式操作系统 现已于2020年9月10日开源 xff0c 并面向应用开发者发布Beta版
  • 宗师级Linux 系统管理员的倾囊相授——《Linux命令行与shell脚本编程大全(第4版)》

    信息安全 早已上升为国家战略 xff0c 发展自主可控的国产操作系统迫在眉睫 为了满足国防 公安等涉密领域对操作系统平台的安全需求 xff0c 国防科技大学研制了以操作系统技术为核心 xff0c 安全可信为特色的中标麒麟 xff08 Ubu
  • Java语言的极限,就是面向对象的极限——《On Java中文版》

    自从1995年问世以来 xff0c Java已经发展成了全世界使用范围最广的语言之一 xff0c 每天都有30亿台运行Java的设备活跃在这个世界上的各个角落里 世界上大多数网站的后台使用Spring开发 xff0c 而Spring开发者必
  • 做后台开发用到的技能都在这儿——《后台开发:核心技术与应用实践》

    大多数面向对象语言没有指针的概念 xff0c C语言也没有对象的概念 xff0c 同时具有指针和对象的 C 43 43 语言在学习时有高昂的门槛 xff0c 同时在服务端后台开发 处理多并发的海量网络请求等方面有天然的优势 就像 Andro
  • Android Canvas 多张图片拼接成长图

    容我慢写
  • matplotlib里的动画

    本文由Mathematrix译自由Jake Vanderplas撰写的Matplotlib Animation Tutorial Matplotlib 1 1 版新添加了一些非常帅的用来制作动画的工具 xff0c 你可以在Matplotli
  • Android Canvas 给图片加上水印

    容我慢写

随机推荐

  • 我做面试官的故事

    2016年就要过完了 xff0c 我入行也快三年了 三年来被人面试过也面试过人 xff0c 我来给大家分享一下我面试别人的两个有趣经历吧 xff1a 1 有一天我穿着环信的T恤 xff0c 前胸是一个巨大的环信logo xff0c 后颈是环
  • 给CheckBox加上动画

    容我慢写
  • Android程序员的十大转型之路

    IT行业是一个瞬息万变的行业 xff0c 程序员是一个不进则退的职业 我作为一个Android程序员 xff0c 多年来一直保持随时可以转型其他技术领域的状态 xff0c 保持对新技术敏感的嗅觉 我先说说Android程序员不可能转型的几个
  • 【玖哥乱弹】编程语言间的斗争

    在初级程序员阶段 xff0c 每个人都不可避免遇到选择编程语言和职业方向的难题 我挑选了几个常见的编程语言 xff0c 分析了优缺点和职业方向 xff0c 以供想当程序员的人参考 C C 43 43 一句话概括 xff1a 大多数中国程序员
  • 【玖哥乱弹】成功的IT人士这样转型AI

    AlphaGo在与围棋世界冠军的对弈大获全胜 xff0c 不但让我们领略到了AI的巨大潜力 xff0c 还把AI推上了新的浪潮之巅 作为一个从即将过去的移动互联网时代走来的Android工程师 xff0c 我深深感受到自己成了传统行业 xf
  • 【玖哥乱弹】程序员如何成为别人的男朋友

    这个世界上程序员数量很多 xff0c 有女朋友的程序员在其中的比例却很少 究其原因 xff0c 不外乎大多数程序员根本不知道怎么才能成为别人的男朋友 成为别人的男朋友对于富二代和拆迁户很容易 xff0c 而对于程序员却很难 xff0c 潘驴
  • wm命令使用方法(修改android 分辨率)修改

    注 xff1a Android 4 3引入的wm工具 wm命令及用法 xff1a 系统说明 xff1a usage wm subcommand options wm size reset WxH wm density reset DENSI
  • 给单个项目单独设置git账号

    一 直接复制带有git账号的项目 直接复制整体项目 其中里面带有 git文件 二 其他方案 暂时没查出来
  • 互联网 Java 工程师面试题之Spring(二)

    Spring 面试题 xff08 二 xff09 1 什么是 spring Spring 是个 java 企业级应用的开源开发框架 Spring 主要用来开发 Java 应用 xff0c 但是有些扩展是针对构建 J2EE 平台的 web 应
  • (IDEA2020 在使用maven时遇到servlet依赖包错误,Error:(6, 37) java: 程序包org.apache.ibatis.annotations不存在)

    IDEA2020 在使用maven时遇到servlet依赖包错误 xff0c Error 6 37 java 程序包org apache ibatis annotations不存在 一 错误显示 xff0c 在本地仓库有依赖的情况下 xff
  • Spring Security(十一) Spring Security 中 CSRF

    从刚开始学习 Spring Security 时 xff0c 在配置类中一直存在这样一行代码 xff1a http csrf disable 如果没有这行代码导致用户无法被认证 这行代码的含义是 xff1a 关闭 csrf 防护 1 什么是
  • 谈谈我对多线程的理解

    一 提到多线程 xff0c 就不得不理解以下几点 xff1a 1 程序 xff0c 进程 xff0c 线程这三者之间的关系 xff1f 简单来说 xff0c 一程序可以调用多个进程 xff0c 比如一个视频播放器程序 xff0c 里面就存在
  • 消费者行为分析包含了哪些内容?

    消费者市场 指个人或家庭为满足生活需求而购买或租用商品的市场 消费者市场特点 1 购买者众多 xff0c 购买数量零星 xff0c 对日用品的消费需要经常性购买 xff0c 购买频率高且量小 xff0c 支付的金额数也小 2 需求差异性大
  • 一个快速从中文文本抽取关键短语的工具 ckpe 提取关键短语

    一个从 中文自然语言文本 中抽取 关键短语 的工具 需要调用的话 xff0c 请直接进入github查看调用方法 xff1a 源码地址 xff1a ckpe 戳这里 61 gt 在线直接试用 关键短语抽取在线版 应用场景 Applicati
  • kali 下libnl-3-dev : 依赖: libnl-3-200 (= 3.2.24-2) 但是 3.2.27-2 正要被安装

    1 先说问题 sudo apt get install libnl span class hljs number 3 span dev 正在读取软件包列表 span class hljs keyword span 完成 正在分析软件包的依赖
  • android的system域解耦

    google很早在为此做准备 xff0c 要求所有设备能够刷GSI xff08 通用系统镜像 xff09 xff0c 并跑过XTS测试 动态分区解耦方案如上图 一 分区描述 单一系统映像 SSI 包含system和system ext图像的
  • Android Activity onConfigurationChanged()方法 监听状态改变

    AndroidManifest xml文件 xff1a 1 增加权限android permission CHANGE CONFIGURATION 2 设置Activity的android configChanges属性 span clas
  • 生产者消费者

    问题意义 生产者消费者问题是一个很经典的问题 xff0c 通过解决此问题 xff0c 能够学到多线程的的知识 程序设计思路 在本程序中采用信号灯的方式 xff0c 用Flag作为标志位 xff0c 指示生产过程和消费过程是否结束 Flag为
  • android keymaster

    keymaster span class hljs keyword is span a newly instroduced key management hardware abstraction layer hal component It
  • Android密钥证书管理相关介绍

    Java Security Java Security是Java中的安全模块 xff0c 它对应了一系列的规范 xff0c 主要包含三个重要规范 xff1a JavaCryptography Extension xff08 简写为JCE x