• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  zcrypt 2.1.0
3  *
4  *  Copyright IBM Corp. 2001, 2012
5  *  Author(s): Robert Burroughs
6  *	       Eric Rossman (edrossma@us.ibm.com)
7  *
8  *  Hotplug & misc device support: Jochen Roehrig (roehrig@de.ibm.com)
9  *  Major cleanup & driver split: Martin Schwidefsky <schwidefsky@de.ibm.com>
10  *				  Ralph Wuerthner <rwuerthn@de.ibm.com>
11  *  MSGTYPE restruct:		  Holger Dengler <hd@linux.vnet.ibm.com>
12  *
13  * This program is free software; you can redistribute it and/or modify
14  * it under the terms of the GNU General Public License as published by
15  * the Free Software Foundation; either version 2, or (at your option)
16  * any later version.
17  *
18  * This program is distributed in the hope that it will be useful,
19  * but WITHOUT ANY WARRANTY; without even the implied warranty of
20  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21  * GNU General Public License for more details.
22  *
23  * You should have received a copy of the GNU General Public License
24  * along with this program; if not, write to the Free Software
25  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
26  */
27 
28 #include <linux/module.h>
29 #include <linux/init.h>
30 #include <linux/err.h>
31 #include <linux/delay.h>
32 #include <linux/slab.h>
33 #include <linux/atomic.h>
34 #include <asm/uaccess.h>
35 
36 #include "ap_bus.h"
37 #include "zcrypt_api.h"
38 #include "zcrypt_error.h"
39 #include "zcrypt_msgtype6.h"
40 #include "zcrypt_pcixcc.h"
41 #include "zcrypt_cca_key.h"
42 
43 #define PCIXCC_MIN_MOD_SIZE	 16	/*  128 bits	*/
44 #define PCIXCC_MIN_MOD_SIZE_OLD	 64	/*  512 bits	*/
45 #define PCIXCC_MAX_MOD_SIZE	256	/* 2048 bits	*/
46 #define CEX3C_MIN_MOD_SIZE	PCIXCC_MIN_MOD_SIZE
47 #define CEX3C_MAX_MOD_SIZE	512	/* 4096 bits	*/
48 
49 #define PCIXCC_MCL2_SPEED_RATING	7870
50 #define PCIXCC_MCL3_SPEED_RATING	7870
51 #define CEX2C_SPEED_RATING		7000
52 #define CEX3C_SPEED_RATING		6500
53 
54 #define PCIXCC_MAX_ICA_MESSAGE_SIZE 0x77c  /* max size type6 v2 crt message */
55 #define PCIXCC_MAX_ICA_RESPONSE_SIZE 0x77c /* max size type86 v2 reply	    */
56 
57 #define PCIXCC_MAX_XCRB_MESSAGE_SIZE (12*1024)
58 
59 #define PCIXCC_CLEANUP_TIME	(15*HZ)
60 
61 #define CEIL4(x) ((((x)+3)/4)*4)
62 
63 struct response_type {
64 	struct completion work;
65 	int type;
66 };
67 #define PCIXCC_RESPONSE_TYPE_ICA  0
68 #define PCIXCC_RESPONSE_TYPE_XCRB 1
69 
70 static struct ap_device_id zcrypt_pcixcc_ids[] = {
71 	{ AP_DEVICE(AP_DEVICE_TYPE_PCIXCC) },
72 	{ AP_DEVICE(AP_DEVICE_TYPE_CEX2C) },
73 	{ AP_DEVICE(AP_DEVICE_TYPE_CEX3C) },
74 	{ /* end of list */ },
75 };
76 
77 MODULE_DEVICE_TABLE(ap, zcrypt_pcixcc_ids);
78 MODULE_AUTHOR("IBM Corporation");
79 MODULE_DESCRIPTION("PCIXCC Cryptographic Coprocessor device driver, " \
80 		   "Copyright IBM Corp. 2001, 2012");
81 MODULE_LICENSE("GPL");
82 
83 static int zcrypt_pcixcc_probe(struct ap_device *ap_dev);
84 static void zcrypt_pcixcc_remove(struct ap_device *ap_dev);
85 
86 static struct ap_driver zcrypt_pcixcc_driver = {
87 	.probe = zcrypt_pcixcc_probe,
88 	.remove = zcrypt_pcixcc_remove,
89 	.ids = zcrypt_pcixcc_ids,
90 	.request_timeout = PCIXCC_CLEANUP_TIME,
91 };
92 
93 /**
94  * Micro-code detection function. Its sends a message to a pcixcc card
95  * to find out the microcode level.
96  * @ap_dev: pointer to the AP device.
97  */
zcrypt_pcixcc_mcl(struct ap_device * ap_dev)98 static int zcrypt_pcixcc_mcl(struct ap_device *ap_dev)
99 {
100 	static unsigned char msg[] = {
101 		0x00,0x06,0x00,0x00,0x00,0x00,0x00,0x00,
102 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
103 		0x00,0x00,0x00,0x58,0x00,0x00,0x00,0x00,
104 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
105 		0x43,0x41,0x00,0x00,0x00,0x00,0x00,0x00,
106 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
107 		0x00,0x00,0x00,0x00,0x50,0x4B,0x00,0x00,
108 		0x00,0x00,0x01,0xC4,0x00,0x00,0x00,0x00,
109 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
110 		0x00,0x00,0x07,0x24,0x00,0x00,0x00,0x00,
111 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
112 		0x00,0xDC,0x02,0x00,0x00,0x00,0x54,0x32,
113 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xE8,
114 		0x00,0x00,0x00,0x00,0x00,0x00,0x07,0x24,
115 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
116 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
117 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
118 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
119 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
120 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
121 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
122 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
123 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
124 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
125 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
126 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
127 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
128 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
129 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
130 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
131 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
132 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
133 		0x00,0x00,0x00,0x04,0x00,0x00,0x00,0x00,
134 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
135 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
136 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
137 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
138 		0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
139 		0x00,0x00,0x00,0x00,0x50,0x4B,0x00,0x0A,
140 		0x4D,0x52,0x50,0x20,0x20,0x20,0x20,0x20,
141 		0x00,0x42,0x00,0x01,0x02,0x03,0x04,0x05,
142 		0x06,0x07,0x08,0x09,0x0A,0x0B,0x0C,0x0D,
143 		0x0E,0x0F,0x00,0x11,0x22,0x33,0x44,0x55,
144 		0x66,0x77,0x88,0x99,0xAA,0xBB,0xCC,0xDD,
145 		0xEE,0xFF,0xFF,0xEE,0xDD,0xCC,0xBB,0xAA,
146 		0x99,0x88,0x77,0x66,0x55,0x44,0x33,0x22,
147 		0x11,0x00,0x01,0x23,0x45,0x67,0x89,0xAB,
148 		0xCD,0xEF,0xFE,0xDC,0xBA,0x98,0x76,0x54,
149 		0x32,0x10,0x00,0x9A,0x00,0x98,0x00,0x00,
150 		0x1E,0x00,0x00,0x94,0x00,0x00,0x00,0x00,
151 		0x04,0x00,0x00,0x8C,0x00,0x00,0x00,0x40,
152 		0x02,0x00,0x00,0x40,0xBA,0xE8,0x23,0x3C,
153 		0x75,0xF3,0x91,0x61,0xD6,0x73,0x39,0xCF,
154 		0x7B,0x6D,0x8E,0x61,0x97,0x63,0x9E,0xD9,
155 		0x60,0x55,0xD6,0xC7,0xEF,0xF8,0x1E,0x63,
156 		0x95,0x17,0xCC,0x28,0x45,0x60,0x11,0xC5,
157 		0xC4,0x4E,0x66,0xC6,0xE6,0xC3,0xDE,0x8A,
158 		0x19,0x30,0xCF,0x0E,0xD7,0xAA,0xDB,0x01,
159 		0xD8,0x00,0xBB,0x8F,0x39,0x9F,0x64,0x28,
160 		0xF5,0x7A,0x77,0x49,0xCC,0x6B,0xA3,0x91,
161 		0x97,0x70,0xE7,0x60,0x1E,0x39,0xE1,0xE5,
162 		0x33,0xE1,0x15,0x63,0x69,0x08,0x80,0x4C,
163 		0x67,0xC4,0x41,0x8F,0x48,0xDF,0x26,0x98,
164 		0xF1,0xD5,0x8D,0x88,0xD9,0x6A,0xA4,0x96,
165 		0xC5,0x84,0xD9,0x30,0x49,0x67,0x7D,0x19,
166 		0xB1,0xB3,0x45,0x4D,0xB2,0x53,0x9A,0x47,
167 		0x3C,0x7C,0x55,0xBF,0xCC,0x85,0x00,0x36,
168 		0xF1,0x3D,0x93,0x53
169 	};
170 	unsigned long long psmid;
171 	struct CPRBX *cprbx;
172 	char *reply;
173 	int rc, i;
174 
175 	reply = (void *) get_zeroed_page(GFP_KERNEL);
176 	if (!reply)
177 		return -ENOMEM;
178 
179 	rc = ap_send(ap_dev->qid, 0x0102030405060708ULL, msg, sizeof(msg));
180 	if (rc)
181 		goto out_free;
182 
183 	/* Wait for the test message to complete. */
184 	for (i = 0; i < 6; i++) {
185 		msleep(300);
186 		rc = ap_recv(ap_dev->qid, &psmid, reply, 4096);
187 		if (rc == 0 && psmid == 0x0102030405060708ULL)
188 			break;
189 	}
190 
191 	if (i >= 6) {
192 		/* Got no answer. */
193 		rc = -ENODEV;
194 		goto out_free;
195 	}
196 
197 	cprbx = (struct CPRBX *) (reply + 48);
198 	if (cprbx->ccp_rtcode == 8 && cprbx->ccp_rscode == 33)
199 		rc = ZCRYPT_PCIXCC_MCL2;
200 	else
201 		rc = ZCRYPT_PCIXCC_MCL3;
202 out_free:
203 	free_page((unsigned long) reply);
204 	return rc;
205 }
206 
207 /**
208  * Large random number detection function. Its sends a message to a pcixcc
209  * card to find out if large random numbers are supported.
210  * @ap_dev: pointer to the AP device.
211  *
212  * Returns 1 if large random numbers are supported, 0 if not and < 0 on error.
213  */
zcrypt_pcixcc_rng_supported(struct ap_device * ap_dev)214 static int zcrypt_pcixcc_rng_supported(struct ap_device *ap_dev)
215 {
216 	struct ap_message ap_msg;
217 	unsigned long long psmid;
218 	struct {
219 		struct type86_hdr hdr;
220 		struct type86_fmt2_ext fmt2;
221 		struct CPRBX cprbx;
222 	} __attribute__((packed)) *reply;
223 	int rc, i;
224 
225 	ap_init_message(&ap_msg);
226 	ap_msg.message = (void *) get_zeroed_page(GFP_KERNEL);
227 	if (!ap_msg.message)
228 		return -ENOMEM;
229 
230 	rng_type6CPRB_msgX(ap_dev, &ap_msg, 4);
231 	rc = ap_send(ap_dev->qid, 0x0102030405060708ULL, ap_msg.message,
232 		     ap_msg.length);
233 	if (rc)
234 		goto out_free;
235 
236 	/* Wait for the test message to complete. */
237 	for (i = 0; i < 2 * HZ; i++) {
238 		msleep(1000 / HZ);
239 		rc = ap_recv(ap_dev->qid, &psmid, ap_msg.message, 4096);
240 		if (rc == 0 && psmid == 0x0102030405060708ULL)
241 			break;
242 	}
243 
244 	if (i >= 2 * HZ) {
245 		/* Got no answer. */
246 		rc = -ENODEV;
247 		goto out_free;
248 	}
249 
250 	reply = ap_msg.message;
251 	if (reply->cprbx.ccp_rtcode == 0 && reply->cprbx.ccp_rscode == 0)
252 		rc = 1;
253 	else
254 		rc = 0;
255 out_free:
256 	free_page((unsigned long) ap_msg.message);
257 	return rc;
258 }
259 
260 /**
261  * Probe function for PCIXCC/CEX2C cards. It always accepts the AP device
262  * since the bus_match already checked the hardware type. The PCIXCC
263  * cards come in two flavours: micro code level 2 and micro code level 3.
264  * This is checked by sending a test message to the device.
265  * @ap_dev: pointer to the AP device.
266  */
zcrypt_pcixcc_probe(struct ap_device * ap_dev)267 static int zcrypt_pcixcc_probe(struct ap_device *ap_dev)
268 {
269 	struct zcrypt_device *zdev;
270 	int rc = 0;
271 
272 	zdev = zcrypt_device_alloc(PCIXCC_MAX_XCRB_MESSAGE_SIZE);
273 	if (!zdev)
274 		return -ENOMEM;
275 	zdev->ap_dev = ap_dev;
276 	zdev->online = 1;
277 	switch (ap_dev->device_type) {
278 	case AP_DEVICE_TYPE_PCIXCC:
279 		rc = zcrypt_pcixcc_mcl(ap_dev);
280 		if (rc < 0) {
281 			zcrypt_device_free(zdev);
282 			return rc;
283 		}
284 		zdev->user_space_type = rc;
285 		if (rc == ZCRYPT_PCIXCC_MCL2) {
286 			zdev->type_string = "PCIXCC_MCL2";
287 			zdev->speed_rating = PCIXCC_MCL2_SPEED_RATING;
288 			zdev->min_mod_size = PCIXCC_MIN_MOD_SIZE_OLD;
289 			zdev->max_mod_size = PCIXCC_MAX_MOD_SIZE;
290 			zdev->max_exp_bit_length = PCIXCC_MAX_MOD_SIZE;
291 		} else {
292 			zdev->type_string = "PCIXCC_MCL3";
293 			zdev->speed_rating = PCIXCC_MCL3_SPEED_RATING;
294 			zdev->min_mod_size = PCIXCC_MIN_MOD_SIZE;
295 			zdev->max_mod_size = PCIXCC_MAX_MOD_SIZE;
296 			zdev->max_exp_bit_length = PCIXCC_MAX_MOD_SIZE;
297 		}
298 		break;
299 	case AP_DEVICE_TYPE_CEX2C:
300 		zdev->user_space_type = ZCRYPT_CEX2C;
301 		zdev->type_string = "CEX2C";
302 		zdev->speed_rating = CEX2C_SPEED_RATING;
303 		zdev->min_mod_size = PCIXCC_MIN_MOD_SIZE;
304 		zdev->max_mod_size = PCIXCC_MAX_MOD_SIZE;
305 		zdev->max_exp_bit_length = PCIXCC_MAX_MOD_SIZE;
306 		break;
307 	case AP_DEVICE_TYPE_CEX3C:
308 		zdev->user_space_type = ZCRYPT_CEX3C;
309 		zdev->type_string = "CEX3C";
310 		zdev->speed_rating = CEX3C_SPEED_RATING;
311 		zdev->min_mod_size = CEX3C_MIN_MOD_SIZE;
312 		zdev->max_mod_size = CEX3C_MAX_MOD_SIZE;
313 		zdev->max_exp_bit_length = CEX3C_MAX_MOD_SIZE;
314 		break;
315 	default:
316 		goto out_free;
317 	}
318 
319 	rc = zcrypt_pcixcc_rng_supported(ap_dev);
320 	if (rc < 0) {
321 		zcrypt_device_free(zdev);
322 		return rc;
323 	}
324 	if (rc)
325 		zdev->ops = zcrypt_msgtype_request(MSGTYPE06_NAME,
326 						   MSGTYPE06_VARIANT_DEFAULT);
327 	else
328 		zdev->ops = zcrypt_msgtype_request(MSGTYPE06_NAME,
329 						   MSGTYPE06_VARIANT_NORNG);
330 	ap_dev->reply = &zdev->reply;
331 	ap_dev->private = zdev;
332 	rc = zcrypt_device_register(zdev);
333 	if (rc)
334 		goto out_free;
335 	return 0;
336 
337  out_free:
338 	ap_dev->private = NULL;
339 	zcrypt_msgtype_release(zdev->ops);
340 	zcrypt_device_free(zdev);
341 	return rc;
342 }
343 
344 /**
345  * This is called to remove the extended PCIXCC/CEX2C driver information
346  * if an AP device is removed.
347  */
zcrypt_pcixcc_remove(struct ap_device * ap_dev)348 static void zcrypt_pcixcc_remove(struct ap_device *ap_dev)
349 {
350 	struct zcrypt_device *zdev = ap_dev->private;
351 	struct zcrypt_ops *zops = zdev->ops;
352 
353 	zcrypt_device_unregister(zdev);
354 	zcrypt_msgtype_release(zops);
355 }
356 
zcrypt_pcixcc_init(void)357 int __init zcrypt_pcixcc_init(void)
358 {
359 	return ap_driver_register(&zcrypt_pcixcc_driver, THIS_MODULE, "pcixcc");
360 }
361 
zcrypt_pcixcc_exit(void)362 void zcrypt_pcixcc_exit(void)
363 {
364 	ap_driver_unregister(&zcrypt_pcixcc_driver);
365 }
366 
367 module_init(zcrypt_pcixcc_init);
368 module_exit(zcrypt_pcixcc_exit);
369