imx-hdmi: Make checkpatch happy
[linux-2.6/btrfs-unstable.git] / drivers / staging / rts5139 / ms_mg.c
blobc8f26062c6824ed9d787cb6dd6c172541af1d2a2
1 /* Driver for Realtek RTS51xx USB card reader
3 * Copyright(c) 2009 Realtek Semiconductor Corp. All rights reserved.
5 * This program is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License as published by the
7 * Free Software Foundation; either version 2, or (at your option) any
8 * later version.
10 * This program is distributed in the hope that it will be useful, but
11 * WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * General Public License for more details.
15 * You should have received a copy of the GNU General Public License along
16 * with this program; if not, see <http://www.gnu.org/licenses/>.
18 * Author:
19 * wwang (wei_wang@realsil.com.cn)
20 * No. 450, Shenhu Road, Suzhou Industry Park, Suzhou, China
21 * Maintainer:
22 * Edwin Rong (edwin_rong@realsil.com.cn)
23 * No. 450, Shenhu Road, Suzhou Industry Park, Suzhou, China
26 #include <linux/blkdev.h>
27 #include <linux/kthread.h>
28 #include <linux/sched.h>
29 #include <linux/slab.h>
31 #include "debug.h"
32 #include "trace.h"
33 #include "rts51x.h"
34 #include "rts51x_transport.h"
35 #include "rts51x_scsi.h"
36 #include "rts51x_card.h"
37 #include "ms.h"
38 #include "ms_mg.h"
40 #ifdef SUPPORT_MAGIC_GATE
42 static int mg_check_int_error(struct rts51x_chip *chip)
44 u8 value;
46 rts51x_read_register(chip, MS_TRANS_CFG, &value);
47 if (value & (INT_ERR | INT_CMDNK))
48 TRACE_RET(chip, STATUS_FAIL);
50 return STATUS_SUCCESS;
53 static int mg_send_ex_cmd(struct rts51x_chip *chip, u8 cmd, u8 entry_num)
55 int retval, i;
56 u8 data[8];
58 data[0] = cmd;
59 data[1] = 0;
60 data[2] = 0;
61 data[3] = 0;
62 data[4] = 0;
63 data[5] = 0;
64 data[6] = entry_num;
65 data[7] = 0;
67 for (i = 0; i < MS_MAX_RETRY_COUNT; i++) {
68 retval =
69 ms_write_bytes(chip, PRO_EX_SET_CMD, 7, WAIT_INT, data, 8);
70 if (retval == STATUS_SUCCESS)
71 break;
73 if (i == MS_MAX_RETRY_COUNT)
74 TRACE_RET(chip, STATUS_FAIL);
75 retval = mg_check_int_error(chip);
76 if (retval != STATUS_SUCCESS)
77 TRACE_RET(chip, STATUS_FAIL);
79 return STATUS_SUCCESS;
82 int rts51x_mg_set_tpc_para_sub(struct rts51x_chip *chip, int type, u8 mg_entry_num)
84 int retval;
85 u8 buf[6];
87 RTS51X_DEBUGP("--%s--\n", __func__);
89 if (type == 0)
90 retval = ms_set_rw_reg_addr(chip, 0, 0, Pro_TPCParm, 1);
91 else
92 retval = ms_set_rw_reg_addr(chip, 0, 0, Pro_DataCount1, 6);
93 if (retval != STATUS_SUCCESS)
94 TRACE_RET(chip, retval);
96 buf[0] = 0;
97 buf[1] = 0;
98 if (type == 1) {
99 buf[2] = 0;
100 buf[3] = 0;
101 buf[4] = 0;
102 buf[5] = mg_entry_num;
104 retval =
105 ms_write_bytes(chip, PRO_WRITE_REG, (type == 0) ? 1 : 6,
106 NO_WAIT_INT, buf, 6);
107 if (retval != STATUS_SUCCESS)
108 TRACE_RET(chip, retval);
110 return STATUS_SUCCESS;
114 * Get MagciGate ID and set Leaf ID to medium.
116 * After receiving this SCSI command, adapter shall fulfill 2 tasks
117 * below in order:
118 * 1. send GET_ID TPC command to get MagicGate ID and hold it till
119 * Response&challenge CMD.
120 * 2. send SET_ID TPC command to medium with Leaf ID released by host
121 * in this SCSI CMD.
123 int rts51x_mg_set_leaf_id(struct scsi_cmnd *srb, struct rts51x_chip *chip)
125 int retval;
126 int i;
127 unsigned int lun = SCSI_LUN(srb);
128 u8 buf1[32], buf2[12];
130 RTS51X_DEBUGP("--%s--\n", __func__);
132 if (scsi_bufflen(srb) < 12) {
133 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MEDIA_INVALID_CMD_FIELD);
134 TRACE_RET(chip, STATUS_FAIL);
136 rts51x_ms_cleanup_work(chip);
138 retval = ms_switch_clock(chip);
139 if (retval != STATUS_SUCCESS)
140 TRACE_RET(chip, retval);
142 retval = mg_send_ex_cmd(chip, MG_SET_LID, 0);
143 if (retval != STATUS_SUCCESS) {
144 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_ESTAB);
145 TRACE_RET(chip, retval);
148 memset(buf1, 0, 32);
149 rts51x_get_xfer_buf(buf2, min(12, (int)scsi_bufflen(srb)), srb);
150 for (i = 0; i < 8; i++)
151 buf1[8 + i] = buf2[4 + i];
152 retval =
153 ms_write_bytes(chip, PRO_WRITE_SHORT_DATA, 32, WAIT_INT, buf1, 32);
154 if (retval != STATUS_SUCCESS) {
155 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_ESTAB);
156 TRACE_RET(chip, retval);
158 retval = mg_check_int_error(chip);
159 if (retval != STATUS_SUCCESS) {
160 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_ESTAB);
161 TRACE_RET(chip, retval);
164 return STATUS_SUCCESS;
168 * Send Local EKB to host.
170 * After receiving this SCSI command, adapter shall read the divided
171 * data(1536 bytes totally) from medium by using READ_LONG_DATA TPC
172 * for 3 times, and report data to host with data-length is 1052 bytes.
174 int rts51x_mg_get_local_EKB(struct scsi_cmnd *srb, struct rts51x_chip *chip)
176 int retval = STATUS_FAIL;
177 int bufflen;
178 unsigned int lun = SCSI_LUN(srb);
179 u8 *buf = NULL;
181 RTS51X_DEBUGP("--%s--\n", __func__);
183 rts51x_ms_cleanup_work(chip);
185 retval = ms_switch_clock(chip);
186 if (retval != STATUS_SUCCESS)
187 TRACE_RET(chip, retval);
189 buf = kmalloc(1540, GFP_KERNEL);
190 if (!buf)
191 TRACE_RET(chip, STATUS_NOMEM);
193 buf[0] = 0x04;
194 buf[1] = 0x1A;
195 buf[2] = 0x00;
196 buf[3] = 0x00;
198 retval = mg_send_ex_cmd(chip, MG_GET_LEKB, 0);
199 if (retval != STATUS_SUCCESS) {
200 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_AUTHEN);
201 TRACE_GOTO(chip, GetEKBFinish);
204 retval = ms_transfer_data(chip, MS_TM_AUTO_READ, PRO_READ_LONG_DATA,
205 3, WAIT_INT, 0, 0, buf + 4, 1536);
206 if (retval != STATUS_SUCCESS) {
207 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_AUTHEN);
208 rts51x_write_register(chip, CARD_STOP, MS_STOP | MS_CLR_ERR,
209 MS_STOP | MS_CLR_ERR);
210 TRACE_GOTO(chip, GetEKBFinish);
212 retval = mg_check_int_error(chip);
213 if (retval != STATUS_SUCCESS) {
214 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_AUTHEN);
215 TRACE_GOTO(chip, GetEKBFinish);
218 bufflen = min(1052, (int)scsi_bufflen(srb));
219 rts51x_set_xfer_buf(buf, bufflen, srb);
221 GetEKBFinish:
222 kfree(buf);
223 return retval;
227 * Send challenge(host) to medium.
229 * After receiving this SCSI command, adapter shall sequentially issues
230 * TPC commands to the medium for writing 8-bytes data as challenge
231 * by host within a short data packet.
233 int rts51x_mg_chg(struct scsi_cmnd *srb, struct rts51x_chip *chip)
235 struct ms_info *ms_card = &(chip->ms_card);
236 int retval;
237 int bufflen;
238 int i;
239 unsigned int lun = SCSI_LUN(srb);
240 u8 buf[32], tmp;
242 RTS51X_DEBUGP("--%s--\n", __func__);
244 rts51x_ms_cleanup_work(chip);
246 retval = ms_switch_clock(chip);
247 if (retval != STATUS_SUCCESS)
248 TRACE_RET(chip, retval);
250 retval = mg_send_ex_cmd(chip, MG_GET_ID, 0);
251 if (retval != STATUS_SUCCESS) {
252 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_INCOMPATIBLE_MEDIUM);
253 TRACE_RET(chip, retval);
256 retval =
257 ms_read_bytes(chip, PRO_READ_SHORT_DATA, 32, WAIT_INT, buf, 32);
258 if (retval != STATUS_SUCCESS) {
259 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_INCOMPATIBLE_MEDIUM);
260 TRACE_RET(chip, retval);
262 retval = mg_check_int_error(chip);
263 if (retval != STATUS_SUCCESS) {
264 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_INCOMPATIBLE_MEDIUM);
265 TRACE_RET(chip, retval);
268 memcpy(ms_card->magic_gate_id, buf, 16);
270 for (i = 0; i < 2500; i++) {
271 RTS51X_READ_REG(chip, MS_TRANS_CFG, &tmp);
272 if (tmp &
273 (MS_INT_CED | MS_INT_CMDNK | MS_INT_BREQ | MS_INT_ERR))
274 break;
276 wait_timeout(1);
279 if (i == 2500) {
280 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_INCOMPATIBLE_MEDIUM);
281 TRACE_RET(chip, STATUS_FAIL);
284 retval = mg_send_ex_cmd(chip, MG_SET_RD, 0);
285 if (retval != STATUS_SUCCESS) {
286 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_INCOMPATIBLE_MEDIUM);
287 TRACE_RET(chip, retval);
290 bufflen = min(12, (int)scsi_bufflen(srb));
291 rts51x_get_xfer_buf(buf, bufflen, srb);
293 for (i = 0; i < 8; i++)
294 buf[i] = buf[4 + i];
295 for (i = 0; i < 24; i++)
296 buf[8 + i] = 0;
297 retval =
298 ms_write_bytes(chip, PRO_WRITE_SHORT_DATA, 32, WAIT_INT, buf, 32);
299 if (retval != STATUS_SUCCESS) {
300 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_INCOMPATIBLE_MEDIUM);
301 TRACE_RET(chip, retval);
303 retval = mg_check_int_error(chip);
304 if (retval != STATUS_SUCCESS) {
305 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_INCOMPATIBLE_MEDIUM);
306 TRACE_RET(chip, retval);
309 ms_card->mg_auth = 0;
311 return STATUS_SUCCESS;
315 * Send Response and Challenge data to host.
317 * After receiving this SCSI command, adapter shall communicates with
318 * the medium, get parameters(HRd, Rms, MagicGateID) by using READ_SHORT_DATA
319 * TPC and send the data to host according to certain format required by
320 * MG-R specification.
321 * The paremeter MagicGateID is the one that adapter has obtained from
322 * the medium by TPC commands in Set Leaf ID command phase previously.
324 int rts51x_mg_get_rsp_chg(struct scsi_cmnd *srb, struct rts51x_chip *chip)
326 struct ms_info *ms_card = &(chip->ms_card);
327 int retval, i;
328 int bufflen;
329 unsigned int lun = SCSI_LUN(srb);
330 u8 buf1[32], buf2[36], tmp;
332 RTS51X_DEBUGP("--%s--\n", __func__);
334 rts51x_ms_cleanup_work(chip);
336 retval = ms_switch_clock(chip);
337 if (retval != STATUS_SUCCESS)
338 TRACE_RET(chip, retval);
340 retval = mg_send_ex_cmd(chip, MG_MAKE_RMS, 0);
341 if (retval != STATUS_SUCCESS) {
342 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_AUTHEN);
343 TRACE_RET(chip, retval);
346 retval =
347 ms_read_bytes(chip, PRO_READ_SHORT_DATA, 32, WAIT_INT, buf1, 32);
348 if (retval != STATUS_SUCCESS) {
349 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_AUTHEN);
350 TRACE_RET(chip, retval);
352 retval = mg_check_int_error(chip);
353 if (retval != STATUS_SUCCESS) {
354 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_AUTHEN);
355 TRACE_RET(chip, retval);
358 buf2[0] = 0x00;
359 buf2[1] = 0x22;
360 buf2[2] = 0x00;
361 buf2[3] = 0x00;
363 memcpy(buf2 + 4, ms_card->magic_gate_id, 16);
364 memcpy(buf2 + 20, buf1, 16);
366 bufflen = min(36, (int)scsi_bufflen(srb));
367 rts51x_set_xfer_buf(buf2, bufflen, srb);
369 for (i = 0; i < 2500; i++) {
370 RTS51X_READ_REG(chip, MS_TRANS_CFG, &tmp);
371 if (tmp & (MS_INT_CED | MS_INT_CMDNK |
372 MS_INT_BREQ | MS_INT_ERR))
373 break;
375 wait_timeout(1);
378 if (i == 2500) {
379 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_AUTHEN);
380 TRACE_RET(chip, STATUS_FAIL);
383 return STATUS_SUCCESS;
387 * Send response(host) to medium.
389 * After receiving this SCSI command, adapter shall sequentially
390 * issues TPC commands to the medium for writing 8-bytes data as
391 * challenge by host within a short data packet.
393 int rts51x_mg_rsp(struct scsi_cmnd *srb, struct rts51x_chip *chip)
395 struct ms_info *ms_card = &(chip->ms_card);
396 int retval;
397 int i;
398 int bufflen;
399 unsigned int lun = SCSI_LUN(srb);
400 u8 buf[32];
402 RTS51X_DEBUGP("--%s--\n", __func__);
404 rts51x_ms_cleanup_work(chip);
406 retval = ms_switch_clock(chip);
407 if (retval != STATUS_SUCCESS)
408 TRACE_RET(chip, retval);
410 retval = mg_send_ex_cmd(chip, MG_MAKE_KSE, 0);
411 if (retval != STATUS_SUCCESS) {
412 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_AUTHEN);
413 TRACE_RET(chip, retval);
416 bufflen = min(12, (int)scsi_bufflen(srb));
417 rts51x_get_xfer_buf(buf, bufflen, srb);
419 for (i = 0; i < 8; i++)
420 buf[i] = buf[4 + i];
421 for (i = 0; i < 24; i++)
422 buf[8 + i] = 0;
423 retval =
424 ms_write_bytes(chip, PRO_WRITE_SHORT_DATA, 32, WAIT_INT, buf, 32);
425 if (retval != STATUS_SUCCESS) {
426 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_AUTHEN);
427 TRACE_RET(chip, retval);
429 retval = mg_check_int_error(chip);
430 if (retval != STATUS_SUCCESS) {
431 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_KEY_FAIL_NOT_AUTHEN);
432 TRACE_RET(chip, retval);
435 ms_card->mg_auth = 1;
437 return STATUS_SUCCESS;
440 /** * Send ICV data to host.
442 * After receiving this SCSI command, adapter shall read the divided
443 * data(1024 bytes totally) from medium by using READ_LONG_DATA TPC
444 * for 2 times, and report data to host with data-length is 1028 bytes.
446 * Since the extra 4 bytes data is just only a prefix to original data
447 * that read from medium, so that the 4-byte data pushed into Ring buffer
448 * precedes data transmission from medium to Ring buffer by DMA mechanism
449 * in order to get maximum performance and minimum code size simultaneously.
451 int rts51x_mg_get_ICV(struct scsi_cmnd *srb, struct rts51x_chip *chip)
453 struct ms_info *ms_card = &(chip->ms_card);
454 int retval;
455 int bufflen;
456 unsigned int lun = SCSI_LUN(srb);
457 u8 *buf = NULL;
459 RTS51X_DEBUGP("--%s--\n", __func__);
461 rts51x_ms_cleanup_work(chip);
463 retval = ms_switch_clock(chip);
464 if (retval != STATUS_SUCCESS)
465 TRACE_RET(chip, retval);
467 buf = kmalloc(1028, GFP_KERNEL);
468 if (!buf)
469 TRACE_RET(chip, STATUS_NOMEM);
471 buf[0] = 0x04;
472 buf[1] = 0x02;
473 buf[2] = 0x00;
474 buf[3] = 0x00;
476 retval = mg_send_ex_cmd(chip, MG_GET_IBD, ms_card->mg_entry_num);
477 if (retval != STATUS_SUCCESS) {
478 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MEDIA_UNRECOVER_READ_ERR);
479 TRACE_GOTO(chip, GetICVFinish);
482 retval = ms_transfer_data(chip, MS_TM_AUTO_READ, PRO_READ_LONG_DATA,
483 2, WAIT_INT, 0, 0, buf + 4, 1024);
484 if (retval != STATUS_SUCCESS) {
485 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MEDIA_UNRECOVER_READ_ERR);
486 rts51x_write_register(chip, CARD_STOP, MS_STOP | MS_CLR_ERR,
487 MS_STOP | MS_CLR_ERR);
488 TRACE_GOTO(chip, GetICVFinish);
490 retval = mg_check_int_error(chip);
491 if (retval != STATUS_SUCCESS) {
492 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MEDIA_UNRECOVER_READ_ERR);
493 TRACE_GOTO(chip, GetICVFinish);
496 bufflen = min(1028, (int)scsi_bufflen(srb));
497 rts51x_set_xfer_buf(buf, bufflen, srb);
499 GetICVFinish:
500 kfree(buf);
501 return retval;
505 * Send ICV data to medium.
507 * After receiving this SCSI command, adapter shall receive 1028 bytes
508 * and write the later 1024 bytes to medium by WRITE_LONG_DATA TPC
509 * consecutively.
511 * Since the first 4-bytes data is just only a prefix to original data
512 * that sent by host, and it should be skipped by shifting DMA pointer
513 * before writing 1024 bytes to medium.
515 int rts51x_mg_set_ICV(struct scsi_cmnd *srb, struct rts51x_chip *chip)
517 struct ms_info *ms_card = &(chip->ms_card);
518 int retval;
519 int bufflen;
520 #ifdef MG_SET_ICV_SLOW
521 int i;
522 #endif
523 unsigned int lun = SCSI_LUN(srb);
524 u8 *buf = NULL;
526 RTS51X_DEBUGP("--%s--\n", __func__);
528 rts51x_ms_cleanup_work(chip);
530 retval = ms_switch_clock(chip);
531 if (retval != STATUS_SUCCESS)
532 TRACE_RET(chip, retval);
534 buf = kmalloc(1028, GFP_KERNEL);
535 if (!buf)
536 TRACE_RET(chip, STATUS_NOMEM);
538 bufflen = min(1028, (int)scsi_bufflen(srb));
539 rts51x_get_xfer_buf(buf, bufflen, srb);
541 retval = mg_send_ex_cmd(chip, MG_SET_IBD, ms_card->mg_entry_num);
542 if (retval != STATUS_SUCCESS) {
543 if (ms_card->mg_auth == 0) {
544 if ((buf[5] & 0xC0) != 0)
545 rts51x_set_sense_type(chip, lun,
546 SENSE_TYPE_MG_KEY_FAIL_NOT_ESTAB);
547 else
548 rts51x_set_sense_type(chip, lun,
549 SENSE_TYPE_MG_WRITE_ERR);
550 } else {
551 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_WRITE_ERR);
553 TRACE_GOTO(chip, SetICVFinish);
556 #ifdef MG_SET_ICV_SLOW
557 for (i = 0; i < 2; i++) {
558 udelay(50);
560 rts51x_init_cmd(chip);
562 rts51x_add_cmd(chip, WRITE_REG_CMD, MS_TPC, 0xFF,
563 PRO_WRITE_LONG_DATA);
564 rts51x_add_cmd(chip, WRITE_REG_CMD, MS_TRANS_CFG, 0xFF,
565 WAIT_INT);
567 rts51x_trans_dma_enable(DMA_TO_DEVICE, chip, 512, DMA_512);
569 rts51x_add_cmd(chip, WRITE_REG_CMD, MS_TRANSFER, 0xFF,
570 MS_TRANSFER_START | MS_TM_NORMAL_WRITE);
571 rts51x_add_cmd(chip, CHECK_REG_CMD, MS_TRANSFER,
572 MS_TRANSFER_END, MS_TRANSFER_END);
574 retval = rts51x_send_cmd(chip, MODE_CDOR, 100);
575 if (retval != STATUS_SUCCESS) {
576 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_WRITE_ERR);
577 TRACE_GOTO(chip, SetICVFinish);
580 retval = rts51x_transfer_data_rcc(chip, SND_BULK_PIPE(chip),
581 buf + 4 + i * 512, 512, 0,
582 NULL, 3000, STAGE_DO);
583 if (retval != STATUS_SUCCESS) {
584 rts51x_clear_ms_error(chip);
585 if (ms_card->mg_auth == 0) {
586 if ((buf[5] & 0xC0) != 0)
587 rts51x_set_sense_type(chip, lun,
588 SENSE_TYPE_MG_KEY_FAIL_NOT_ESTAB);
589 else
590 rts51x_set_sense_type(chip, lun,
591 SENSE_TYPE_MG_WRITE_ERR);
592 } else {
593 rts51x_set_sense_type(chip, lun,
594 SENSE_TYPE_MG_WRITE_ERR);
596 retval = STATUS_FAIL;
597 TRACE_GOTO(chip, SetICVFinish);
600 retval = rts51x_get_rsp(chip, 1, 3000);
601 if (CHECK_MS_TRANS_FAIL(chip, retval)
602 || mg_check_int_error(chip)) {
603 rts51x_clear_ms_error(chip);
604 if (ms_card->mg_auth == 0) {
605 if ((buf[5] & 0xC0) != 0)
606 rts51x_set_sense_type(chip, lun,
607 SENSE_TYPE_MG_KEY_FAIL_NOT_ESTAB);
608 else
609 rts51x_set_sense_type(chip, lun,
610 SENSE_TYPE_MG_WRITE_ERR);
611 } else {
612 rts51x_set_sense_type(chip, lun,
613 SENSE_TYPE_MG_WRITE_ERR);
615 retval = STATUS_FAIL;
616 TRACE_GOTO(chip, SetICVFinish);
619 #else
620 retval = ms_transfer_data(chip, MS_TM_AUTO_WRITE, PRO_WRITE_LONG_DATA,
621 2, WAIT_INT, 0, 0, buf + 4, 1024);
622 if (retval != STATUS_SUCCESS) {
623 rts51x_clear_ms_error(chip);
624 if (ms_card->mg_auth == 0) {
625 if ((buf[5] & 0xC0) != 0)
626 rts51x_set_sense_type(chip, lun,
627 SENSE_TYPE_MG_KEY_FAIL_NOT_ESTAB);
628 else
629 rts51x_set_sense_type(chip, lun,
630 SENSE_TYPE_MG_WRITE_ERR);
631 } else {
632 rts51x_set_sense_type(chip, lun, SENSE_TYPE_MG_WRITE_ERR);
634 TRACE_GOTO(chip, SetICVFinish);
636 #endif
638 SetICVFinish:
639 kfree(buf);
640 return retval;
643 #endif /* SUPPORT_MAGIC_GATE */