1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18#define VERSION "v4.63 Andrew J. Kroll <ag784@freenet.buffalo.edu> Wed Jul 26 04:24:10 EDT 2000"
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349#define DONT_MERGE_REQUESTS
350
351#ifndef SBPCD_ISSUE
352#define SBPCD_ISSUE 1
353#endif
354
355#include <linux/module.h>
356
357#include <linux/version.h>
358#include <linux/errno.h>
359#include <linux/sched.h>
360#include <linux/mm.h>
361#include <linux/timer.h>
362#include <linux/fs.h>
363#include <linux/kernel.h>
364#include <linux/cdrom.h>
365#include <linux/ioport.h>
366#include <linux/devfs_fs_kernel.h>
367#include <linux/major.h>
368#include <linux/string.h>
369#include <linux/vmalloc.h>
370#include <linux/init.h>
371#include <linux/interrupt.h>
372
373#include <asm/system.h>
374#include <asm/io.h>
375#include <asm/uaccess.h>
376#include <stdarg.h>
377#include <linux/config.h>
378#include "sbpcd.h"
379
380#if !(SBPCD_ISSUE-1)
381#define MAJOR_NR MATSUSHITA_CDROM_MAJOR
382#endif
383#if !(SBPCD_ISSUE-2)
384#define MAJOR_NR MATSUSHITA_CDROM2_MAJOR
385#endif
386#if !(SBPCD_ISSUE-3)
387#define MAJOR_NR MATSUSHITA_CDROM3_MAJOR
388#endif
389#if !(SBPCD_ISSUE-4)
390#define MAJOR_NR MATSUSHITA_CDROM4_MAJOR
391#endif
392
393#include <linux/blk.h>
394
395
396
397
398
399
400#if !(SBPCD_ISSUE-1)
401#define DO_SBPCD_REQUEST(a) do_sbpcd_request(a)
402#define SBPCD_INIT(a) sbpcd_init(a)
403#endif
404#if !(SBPCD_ISSUE-2)
405#define DO_SBPCD_REQUEST(a) do_sbpcd2_request(a)
406#define SBPCD_INIT(a) sbpcd2_init(a)
407#endif
408#if !(SBPCD_ISSUE-3)
409#define DO_SBPCD_REQUEST(a) do_sbpcd3_request(a)
410#define SBPCD_INIT(a) sbpcd3_init(a)
411#endif
412#if !(SBPCD_ISSUE-4)
413#define DO_SBPCD_REQUEST(a) do_sbpcd4_request(a)
414#define SBPCD_INIT(a) sbpcd4_init(a)
415#endif
416
417#if SBPCD_DIS_IRQ
418#define SBPCD_CLI cli()
419#define SBPCD_STI sti()
420#else
421#define SBPCD_CLI
422#define SBPCD_STI
423#endif
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441#if !(SBPCD_ISSUE-1)
442static int sbpcd[] =
443{
444 CDROM_PORT, SBPRO,
445#if DISTRIBUTION
446 0x230, 1,
447#if 0
448 0x300, 0,
449
450 0x250, 1,
451 0x2C0, 3,
452 0x260, 1,
453 0x320, 0,
454
455 0x338, 0,
456 0x340, 0,
457 0x360, 0,
458 0x270, 1,
459 0x670, 0,
460 0x690, 0,
461 0x338, 2,
462 0x328, 2,
463 0x348, 2,
464 0x634, 0,
465 0x638, 0,
466 0x230, 1,
467
468 0x630, 0,
469 0x650, 0,
470#ifdef MODULE
471
472
473
474
475 0x330, 0,
476 0x350, 0,
477 0x358, 2,
478 0x370, 0,
479 0x290, 1,
480 0x310, 0,
481#endif
482#endif
483#endif
484};
485#else
486static int sbpcd[] = {CDROM_PORT, SBPRO};
487#endif
488MODULE_PARM(sbpcd, "2i");
489MODULE_PARM(max_drives, "i");
490
491#define NUM_PROBE (sizeof(sbpcd) / sizeof(int))
492
493
494
495
496
497#if !(SBPCD_ISSUE-1)
498#ifdef CONFIG_SBPCD2
499extern int sbpcd2_init(void);
500#endif
501#ifdef CONFIG_SBPCD3
502extern int sbpcd3_init(void);
503#endif
504#ifdef CONFIG_SBPCD4
505extern int sbpcd4_init(void);
506#endif
507#endif
508
509
510
511#define INLINE inline
512
513
514
515
516
517static void sbp_sleep(u_int);
518static void mark_timeout_delay(u_long);
519static void mark_timeout_data(u_long);
520#if 0
521static void mark_timeout_audio(u_long);
522#endif
523static void sbp_read_cmd(struct request *req);
524static int sbp_data(struct request *req);
525static int cmd_out(void);
526static int DiskInfo(void);
527static int sbpcd_chk_disk_change(kdev_t);
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566#if DISTRIBUTION
567static int sbpcd_debug = (1<<DBG_INF);
568#else
569static int sbpcd_debug = 0 & ((1<<DBG_INF) |
570 (1<<DBG_TOC) |
571 (1<<DBG_MUL) |
572 (1<<DBG_UPC));
573#endif
574
575static int sbpcd_ioaddr = CDROM_PORT;
576static int sbpro_type = SBPRO;
577static unsigned char f_16bit;
578static unsigned char do_16bit;
579static int CDo_command, CDo_reset;
580static int CDo_sel_i_d, CDo_enable;
581static int CDi_info, CDi_status, CDi_data;
582static struct cdrom_msf msf;
583static struct cdrom_ti ti;
584static struct cdrom_tochdr tochdr;
585static struct cdrom_tocentry tocentry;
586static struct cdrom_subchnl SC;
587static struct cdrom_volctrl volctrl;
588static struct cdrom_read_audio read_audio;
589
590static unsigned char msgnum;
591static char msgbuf[80];
592
593static int max_drives = MAX_DRIVES;
594#ifndef MODULE
595static unsigned char setup_done;
596static const char *str_sb_l = "soundblaster";
597static const char *str_sp_l = "spea";
598static const char *str_ss_l = "soundscape";
599static const char *str_t16_l = "teac16bit";
600static const char *str_ss = "SoundScape";
601#endif
602static const char *str_sb = "SoundBlaster";
603static const char *str_lm = "LaserMate";
604static const char *str_sp = "SPEA";
605static const char *str_t16 = "Teac16bit";
606static const char *type;
607
608#if !(SBPCD_ISSUE-1)
609static const char *major_name="sbpcd";
610#endif
611#if !(SBPCD_ISSUE-2)
612static const char *major_name="sbpcd2";
613#endif
614#if !(SBPCD_ISSUE-3)
615static const char *major_name="sbpcd3";
616#endif
617#if !(SBPCD_ISSUE-4)
618static const char *major_name="sbpcd4";
619#endif
620
621
622
623#if FUTURE
624static DECLARE_WAIT_QUEUE_HEAD(sbp_waitq);
625#endif
626
627static int teac=SBP_TEAC_SPEED;
628static int buffers=SBP_BUFFER_FRAMES;
629
630static u_char family0[]="MATSHITA";
631static u_char family1[]="CR-56";
632static u_char family2[]="CD200";
633static u_char familyL[]="LCS-7260";
634static u_char familyT[]="CD-55";
635static u_char familyV[]="ECS-AT";
636
637static u_int recursion;
638static u_int fatal_err;
639static u_int response_count;
640static u_int flags_cmd_out;
641static u_char cmd_type;
642static u_char drvcmd[10];
643static u_char infobuf[20];
644static u_char xa_head_buf[CD_XA_HEAD];
645static u_char xa_tail_buf[CD_XA_TAIL];
646
647#if OLD_BUSY
648static volatile u_char busy_data;
649static volatile u_char busy_audio;
650#endif
651static DECLARE_MUTEX(ioctl_read_sem);
652static u_long timeout;
653static volatile u_char timed_out_delay;
654static volatile u_char timed_out_data;
655#if 0
656static volatile u_char timed_out_audio;
657#endif
658static u_int datarate= 1000000;
659static u_int maxtim16=16000000;
660static u_int maxtim04= 4000000;
661static u_int maxtim02= 2000000;
662static u_int maxtim_8= 30000;
663#if LONG_TIMING
664static u_int maxtim_data= 9000;
665#else
666static u_int maxtim_data= 3000;
667#endif
668#if DISTRIBUTION
669static int n_retries=6;
670#else
671static int n_retries=6;
672#endif
673
674
675static int ndrives;
676static u_char drv_pattern[NR_SBPCD]={speed_auto,speed_auto,speed_auto,speed_auto};
677static int sbpcd_blocksizes[NR_SBPCD];
678
679
680
681
682
683static int d;
684
685static struct {
686 char drv_id;
687 char drv_sel;
688
689 char drive_model[9];
690 u_char firmware_version[4];
691 char f_eject;
692 u_char *sbp_buf;
693
694 u_int sbp_bufsiz;
695 int sbp_first_frame;
696 int sbp_last_frame;
697 int sbp_read_frames;
698 int sbp_current;
699
700 u_char mode;
701 u_char *aud_buf;
702
703 u_int sbp_audsiz;
704 u_int drv_type;
705 u_char drv_options;
706 int status_bits;
707 u_char diskstate_flags;
708 u_char sense_byte;
709
710 u_char CD_changed;
711 char open_count;
712 u_char error_byte;
713
714 u_char f_multisession;
715 u_int lba_multi;
716 int first_session;
717 int last_session;
718 int track_of_last_session;
719
720 u_char audio_state;
721 u_int pos_audio_start;
722 u_int pos_audio_end;
723 char vol_chan0;
724 u_char vol_ctrl0;
725 char vol_chan1;
726 u_char vol_ctrl1;
727#if 000
728 char vol_chan2;
729 u_char vol_ctrl2;
730 char vol_chan3;
731 u_char vol_ctrl3;
732#endif
733 u_char volume_control;
734
735 u_char SubQ_ctl_adr;
736 u_char SubQ_trk;
737 u_char SubQ_pnt_idx;
738 u_int SubQ_run_tot;
739 u_int SubQ_run_trk;
740 u_char SubQ_whatisthis;
741
742 u_char UPC_ctl_adr;
743 u_char UPC_buf[7];
744
745 int frame_size;
746 int CDsize_frm;
747
748 u_char xa_byte;
749 u_char n_first_track;
750 u_char n_last_track;
751 u_int size_msf;
752 u_int size_blk;
753
754 u_char TocEnt_nixbyte;
755 u_char TocEnt_ctl_adr;
756 u_char TocEnt_number;
757 u_char TocEnt_format;
758 u_int TocEnt_address;
759#if SAFE_MIXED
760 char has_data;
761#endif
762 u_char ored_ctl_adr;
763
764 struct {
765 u_char nixbyte;
766 u_char ctl_adr;
767 u_char number;
768 u_char format;
769 u_int address;
770 } TocBuffer[MAX_TRACKS+1];
771
772 int in_SpinUp;
773 int n_bytes;
774 u_char error_state, b3, b4;
775 u_char f_drv_error;
776 u_char speed_byte;
777 int frmsiz;
778 u_char f_XA;
779 u_char type_byte;
780 u_char mode_xb_6;
781 u_char mode_yb_7;
782 u_char mode_xb_8;
783 u_char delay;
784 struct cdrom_device_info *sbpcd_infop;
785
786} D_S[NR_SBPCD];
787
788
789
790
791
792#if 0
793unsigned long cli_sti;
794#endif
795
796static struct timer_list delay_timer = { function: mark_timeout_delay};
797static struct timer_list data_timer = { function: mark_timeout_data};
798#if 0
799static struct timer_list audio_timer = { function: mark_timeout_audio};
800#endif
801
802
803
804
805static void msg(int level, const char *fmt, ...)
806{
807#if DISTRIBUTION
808#define MSG_LEVEL KERN_NOTICE
809#else
810#define MSG_LEVEL KERN_INFO
811#endif
812
813 char buf[256];
814 va_list args;
815
816 if (!(sbpcd_debug&(1<<level))) return;
817
818 msgnum++;
819 if (msgnum>99) msgnum=0;
820 sprintf(buf, MSG_LEVEL "%s-%d [%02d]: ", major_name, d, msgnum);
821 va_start(args, fmt);
822 vsprintf(&buf[18], fmt, args);
823 va_end(args);
824 printk(buf);
825#if KLOGD_PAUSE
826 sbp_sleep(KLOGD_PAUSE);
827#endif
828 return;
829}
830
831
832
833
834static int sbpcd_dbg_ioctl(unsigned long arg, int level)
835{
836 switch(arg)
837 {
838 case 0:
839 sbpcd_debug = DBG_INF;
840 break;
841
842 default:
843 if (arg>=128) sbpcd_debug &= ~(1<<(arg-128));
844 else sbpcd_debug |= (1<<arg);
845 }
846 return (arg);
847}
848
849static void mark_timeout_delay(u_long i)
850{
851 timed_out_delay=1;
852#if 0
853 msg(DBG_TIM,"delay timer expired.\n");
854#endif
855}
856
857static void mark_timeout_data(u_long i)
858{
859 timed_out_data=1;
860#if 0
861 msg(DBG_TIM,"data timer expired.\n");
862#endif
863}
864
865#if 0
866static void mark_timeout_audio(u_long i)
867{
868 timed_out_audio=1;
869#if 0
870 msg(DBG_TIM,"audio timer expired.\n");
871#endif
872}
873#endif
874
875
876
877
878static void sbp_sleep(u_int time)
879{
880 sti();
881 current->state = TASK_INTERRUPTIBLE;
882 schedule_timeout(time);
883 sti();
884}
885
886#define RETURN_UP(rc) {up(&ioctl_read_sem); return(rc);}
887
888
889
890
891static INLINE void lba2msf(int lba, u_char *msf)
892{
893 lba += CD_MSF_OFFSET;
894 msf[0] = lba / (CD_SECS*CD_FRAMES);
895 lba %= CD_SECS*CD_FRAMES;
896 msf[1] = lba / CD_FRAMES;
897 msf[2] = lba % CD_FRAMES;
898}
899
900
901
902
903
904static INLINE void bin2bcdx(u_char *p)
905{
906 *p=((*p/10)<<4)|(*p%10);
907}
908
909static INLINE u_int blk2msf(u_int blk)
910{
911 MSF msf;
912 u_int mm;
913
914 msf.c[3] = 0;
915 msf.c[2] = (blk + CD_MSF_OFFSET) / (CD_SECS * CD_FRAMES);
916 mm = (blk + CD_MSF_OFFSET) % (CD_SECS * CD_FRAMES);
917 msf.c[1] = mm / CD_FRAMES;
918 msf.c[0] = mm % CD_FRAMES;
919 return (msf.n);
920}
921
922static INLINE u_int make16(u_char rh, u_char rl)
923{
924 return ((rh<<8)|rl);
925}
926
927static INLINE u_int make32(u_int rh, u_int rl)
928{
929 return ((rh<<16)|rl);
930}
931
932static INLINE u_char swap_nibbles(u_char i)
933{
934 return ((i<<4)|(i>>4));
935}
936
937static INLINE u_char byt2bcd(u_char i)
938{
939 return (((i/10)<<4)+i%10);
940}
941
942static INLINE u_char bcd2bin(u_char bcd)
943{
944 return ((bcd>>4)*10+(bcd&0x0F));
945}
946
947static INLINE int msf2blk(int msfx)
948{
949 MSF msf;
950 int i;
951
952 msf.n=msfx;
953 i=(msf.c[2] * CD_SECS + msf.c[1]) * CD_FRAMES + msf.c[0] - CD_MSF_OFFSET;
954 if (i<0) return (0);
955 return (i);
956}
957
958
959
960
961static INLINE int msf2lba(u_char *msf)
962{
963 int i;
964
965 i=(msf[0] * CD_SECS + msf[1]) * CD_FRAMES + msf[2] - CD_MSF_OFFSET;
966 if (i<0) return (0);
967 return (i);
968}
969
970
971static int sta2err(int sta)
972{
973 if (famT_drive)
974 {
975 if (sta==0x00) return (0);
976 if (sta==0x01) return (-604);
977 if (sta==0x02) return (-602);
978 if (sta==0x03) return (-607);
979 if (sta==0x04) return (-612);
980 if (sta==0x05) return (0);
981 if (sta==0x06) return (-ERR_DISKCHANGE);
982 if (sta==0x0b) return (-612);
983 if (sta==0xff) return (-612);
984 return (0);
985 }
986 else
987 {
988 if (sta<=2) return (sta);
989 if (sta==0x05) return (-604);
990 if (sta==0x06) return (-606);
991 if (sta==0x0d) return (-606);
992 if (sta==0x0e) return (-603);
993 if (sta==0x14) return (-603);
994 if (sta==0x0c) return (-611);
995 if (sta==0x0f) return (-611);
996 if (sta==0x10) return (-611);
997 if (sta>=0x16) return (-612);
998 if (sta==0x11) return (-ERR_DISKCHANGE);
999 if (famL_drive)
1000 if (sta==0x12) return (-ERR_DISKCHANGE);
1001 return (-602);
1002 }
1003}
1004
1005static INLINE void clr_cmdbuf(void)
1006{
1007 int i;
1008
1009 for (i=0;i<10;i++) drvcmd[i]=0;
1010 cmd_type=0;
1011}
1012
1013static void flush_status(void)
1014{
1015 int i;
1016
1017 sbp_sleep(15*HZ/10);
1018 for (i=maxtim_data;i!=0;i--) inb(CDi_status);
1019}
1020
1021
1022
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
1033
1034
1035static int CDi_stat_loop_T(void)
1036{
1037 int i, gear=1;
1038 u_long timeout_1, timeout_2, timeout_3, timeout_4;
1039
1040 timeout_1 = jiffies + HZ / 50;
1041 timeout_2 = jiffies + HZ / 5;
1042 timeout_3 = jiffies + 5 * HZ;
1043 timeout_4 = jiffies + 45 * HZ;
1044 do
1045 {
1046 i = inb(CDi_status);
1047 if (!(i&s_not_data_ready)) return (i);
1048 if (!(i&s_not_result_ready)) return (i);
1049 switch(gear)
1050 {
1051 case 4:
1052 sbp_sleep(HZ);
1053 if (time_after(jiffies, timeout_4)) gear++;
1054 msg(DBG_TEA, "CDi_stat_loop_T: long sleep active.\n");
1055 break;
1056 case 3:
1057 sbp_sleep(HZ/10);
1058 if (time_after(jiffies, timeout_3)) gear++;
1059 break;
1060 case 2:
1061 sbp_sleep(HZ/100);
1062 if (time_after(jiffies, timeout_2)) gear++;
1063 break;
1064 case 1:
1065 sbp_sleep(0);
1066 if (time_after(jiffies, timeout_1)) gear++;
1067 }
1068 } while (gear < 5);
1069 return -1;
1070}
1071
1072static int CDi_stat_loop(void)
1073{
1074 int i,j;
1075
1076 for(timeout = jiffies + 10*HZ, i=maxtim_data; time_before(jiffies, timeout); )
1077 {
1078 for ( ;i!=0;i--)
1079 {
1080 j=inb(CDi_status);
1081 if (!(j&s_not_data_ready)) return (j);
1082 if (!(j&s_not_result_ready)) return (j);
1083 if (fam0L_drive) if (j&s_attention) return (j);
1084 }
1085 sbp_sleep(1);
1086 i = 1;
1087 }
1088 msg(DBG_LCS,"CDi_stat_loop failed in line %d\n", __LINE__);
1089 return (-1);
1090}
1091
1092#if 00000
1093
1094static int tst_DataReady(void)
1095{
1096 int i;
1097
1098 i=inb(CDi_status);
1099 if (i&s_not_data_ready) return (0);
1100 return (1);
1101}
1102
1103static int tst_ResultReady(void)
1104{
1105 int i;
1106
1107 i=inb(CDi_status);
1108 if (i&s_not_result_ready) return (0);
1109 return (1);
1110}
1111
1112static int tst_Attention(void)
1113{
1114 int i;
1115
1116 i=inb(CDi_status);
1117 if (i&s_attention) return (1);
1118 return (0);
1119}
1120
1121#endif
1122
1123static int ResponseInfo(void)
1124{
1125 int i,j,st=0;
1126 u_long timeout;
1127
1128 for (i=0,timeout=jiffies+HZ;i<response_count;i++)
1129 {
1130 for (j=maxtim_data; ; )
1131 {
1132 for ( ;j!=0;j-- )
1133 {
1134 st=inb(CDi_status);
1135 if (!(st&s_not_result_ready)) break;
1136 }
1137 if ((j!=0)||time_after_eq(jiffies, timeout)) break;
1138 sbp_sleep(1);
1139 j = 1;
1140 }
1141 if (time_after_eq(jiffies, timeout)) break;
1142 infobuf[i]=inb(CDi_info);
1143 }
1144#if 000
1145 while (!(inb(CDi_status)&s_not_result_ready))
1146 {
1147 infobuf[i++]=inb(CDi_info);
1148 }
1149 j=i-response_count;
1150 if (j>0) msg(DBG_INF,"ResponseInfo: got %d trailing bytes.\n",j);
1151#endif
1152 for (j=0;j<i;j++)
1153 sprintf(&msgbuf[j*3]," %02X",infobuf[j]);
1154 msgbuf[j*3]=0;
1155 msg(DBG_CMD,"ResponseInfo:%s (%d,%d)\n",msgbuf,response_count,i);
1156 j=response_count-i;
1157 if (j>0) return (-j);
1158 else return (i);
1159}
1160
1161static void EvaluateStatus(int st)
1162{
1163 D_S[d].status_bits=0;
1164 if (fam1_drive) D_S[d].status_bits=st|p_success;
1165 else if (fam0_drive)
1166 {
1167 if (st&p_caddin_old) D_S[d].status_bits |= p_door_closed|p_caddy_in;
1168 if (st&p_spinning) D_S[d].status_bits |= p_spinning;
1169 if (st&p_check) D_S[d].status_bits |= p_check;
1170 if (st&p_success_old) D_S[d].status_bits |= p_success;
1171 if (st&p_busy_old) D_S[d].status_bits |= p_busy_new;
1172 if (st&p_disk_ok) D_S[d].status_bits |= p_disk_ok;
1173 }
1174 else if (famLV_drive)
1175 {
1176 D_S[d].status_bits |= p_success;
1177 if (st&p_caddin_old) D_S[d].status_bits |= p_disk_ok|p_caddy_in;
1178 if (st&p_spinning) D_S[d].status_bits |= p_spinning;
1179 if (st&p_check) D_S[d].status_bits |= p_check;
1180 if (st&p_busy_old) D_S[d].status_bits |= p_busy_new;
1181 if (st&p_lcs_door_closed) D_S[d].status_bits |= p_door_closed;
1182 if (st&p_lcs_door_locked) D_S[d].status_bits |= p_door_locked;
1183 }
1184 else if (fam2_drive)
1185 {
1186 D_S[d].status_bits |= p_success;
1187 if (st&p2_check) D_S[d].status_bits |= p1_check;
1188 if (st&p2_door_closed) D_S[d].status_bits |= p1_door_closed;
1189 if (st&p2_disk_in) D_S[d].status_bits |= p1_disk_in;
1190 if (st&p2_busy1) D_S[d].status_bits |= p1_busy;
1191 if (st&p2_busy2) D_S[d].status_bits |= p1_busy;
1192 if (st&p2_spinning) D_S[d].status_bits |= p1_spinning;
1193 if (st&p2_door_locked) D_S[d].status_bits |= p1_door_locked;
1194 if (st&p2_disk_ok) D_S[d].status_bits |= p1_disk_ok;
1195 }
1196 else if (famT_drive)
1197 {
1198 return;
1199 D_S[d].status_bits |= p_success;
1200 if (st&p2_check) D_S[d].status_bits |= p1_check;
1201 if (st&p2_door_closed) D_S[d].status_bits |= p1_door_closed;
1202 if (st&p2_disk_in) D_S[d].status_bits |= p1_disk_in;
1203 if (st&p2_busy1) D_S[d].status_bits |= p1_busy;
1204 if (st&p2_busy2) D_S[d].status_bits |= p1_busy;
1205 if (st&p2_spinning) D_S[d].status_bits |= p1_spinning;
1206 if (st&p2_door_locked) D_S[d].status_bits |= p1_door_locked;
1207 if (st&p2_disk_ok) D_S[d].status_bits |= p1_disk_ok;
1208 }
1209 return;
1210}
1211
1212static int get_state_T(void)
1213{
1214 int i;
1215
1216 static int cmd_out_T(void);
1217
1218 clr_cmdbuf();
1219 D_S[d].n_bytes=1;
1220 drvcmd[0]=CMDT_STATUS;
1221 i=cmd_out_T();
1222 if (i>=0) i=infobuf[0];
1223 else
1224 {
1225 msg(DBG_TEA,"get_state_T error %d\n", i);
1226 return (i);
1227 }
1228 if (i>=0)
1229
1230 D_S[d].status_bits=p1_door_closed|p1_disk_in|p1_spinning|p1_disk_ok;
1231 else if (D_S[d].error_state==6)
1232 {
1233
1234 D_S[d].status_bits=p1_door_closed|p1_disk_in;
1235 D_S[d].CD_changed=0xFF;
1236 D_S[d].diskstate_flags &= ~toc_bit;
1237 }
1238 else if ((D_S[d].error_state!=2)||(D_S[d].b3!=0x3A)||(D_S[d].b4==0x00))
1239 {
1240
1241 D_S[d].status_bits=p1_door_closed;
1242 D_S[d].open_count=0;
1243 }
1244 else if (D_S[d].b4==0x01)
1245 {
1246
1247 D_S[d].status_bits=0;
1248 D_S[d].open_count=0;
1249 }
1250 else
1251 {
1252
1253 D_S[d].status_bits=p1_door_closed;
1254 D_S[d].open_count=0;
1255 }
1256 return (D_S[d].status_bits);
1257}
1258
1259static int ResponseStatus(void)
1260{
1261 int i,j;
1262 u_long timeout;
1263
1264 msg(DBG_STA,"doing ResponseStatus...\n");
1265 if (famT_drive) return (get_state_T());
1266 if (flags_cmd_out & f_respo3) timeout = jiffies;
1267 else if (flags_cmd_out & f_respo2) timeout = jiffies + 16*HZ;
1268 else timeout = jiffies + 4*HZ;
1269 j=maxtim_8;
1270 do
1271 {
1272 for ( ;j!=0;j--)
1273 {
1274 i=inb(CDi_status);
1275 if (!(i&s_not_result_ready)) break;
1276 }
1277 if ((j!=0)||time_after(jiffies, timeout)) break;
1278 sbp_sleep(1);
1279 j = 1;
1280 }
1281 while (1);
1282 if (j==0)
1283 {
1284 if ((flags_cmd_out & f_respo3) == 0)
1285 msg(DBG_STA,"ResponseStatus: timeout.\n");
1286 D_S[d].status_bits=0;
1287 return (-401);
1288 }
1289 i=inb(CDi_info);
1290 msg(DBG_STA,"ResponseStatus: response %02X.\n", i);
1291 EvaluateStatus(i);
1292 msg(DBG_STA,"status_bits=%02X, i=%02X\n",D_S[d].status_bits,i);
1293 return (D_S[d].status_bits);
1294}
1295
1296static void cc_ReadStatus(void)
1297{
1298 int i;
1299
1300 msg(DBG_STA,"giving cc_ReadStatus command\n");
1301 if (famT_drive) return;
1302 SBPCD_CLI;
1303 if (fam0LV_drive) OUT(CDo_command,CMD0_STATUS);
1304 else if (fam1_drive) OUT(CDo_command,CMD1_STATUS);
1305 else if (fam2_drive) OUT(CDo_command,CMD2_STATUS);
1306 if (!fam0LV_drive) for (i=0;i<6;i++) OUT(CDo_command,0);
1307 SBPCD_STI;
1308}
1309
1310static int cc_ReadError(void)
1311{
1312 int i;
1313
1314 clr_cmdbuf();
1315 msg(DBG_ERR,"giving cc_ReadError command.\n");
1316 if (fam1_drive)
1317 {
1318 drvcmd[0]=CMD1_READ_ERR;
1319 response_count=8;
1320 flags_cmd_out=f_putcmd|f_ResponseStatus;
1321 }
1322 else if (fam0LV_drive)
1323 {
1324 drvcmd[0]=CMD0_READ_ERR;
1325 response_count=6;
1326 if (famLV_drive)
1327 flags_cmd_out=f_putcmd;
1328 else
1329 flags_cmd_out=f_putcmd|f_getsta|f_ResponseStatus;
1330 }
1331 else if (fam2_drive)
1332 {
1333 drvcmd[0]=CMD2_READ_ERR;
1334 response_count=6;
1335 flags_cmd_out=f_putcmd;
1336 }
1337 else if (famT_drive)
1338 {
1339 response_count=5;
1340 drvcmd[0]=CMDT_READ_ERR;
1341 }
1342 i=cmd_out();
1343 D_S[d].error_byte=0;
1344 msg(DBG_ERR,"cc_ReadError: cmd_out(CMDx_READ_ERR) returns %d (%02X)\n",i,i);
1345 if (i<0) return (i);
1346 if (fam0V_drive) i=1;
1347 else i=2;
1348 D_S[d].error_byte=infobuf[i];
1349 msg(DBG_ERR,"cc_ReadError: infobuf[%d] is %d (%02X)\n",i,D_S[d].error_byte,D_S[d].error_byte);
1350 i=sta2err(infobuf[i]);
1351 if (i==-ERR_DISKCHANGE)
1352 {
1353 D_S[d].CD_changed=0xFF;
1354 D_S[d].diskstate_flags &= ~toc_bit;
1355 }
1356 return (i);
1357}
1358
1359static int cmd_out_T(void)
1360{
1361#undef CMDT_TRIES
1362#define CMDT_TRIES 1000
1363#define TEST_FALSE_FF 1
1364
1365 static int cc_DriveReset(void);
1366 int i, j, l=0, m, ntries;
1367 long flags;
1368
1369 D_S[d].error_state=0;
1370 D_S[d].b3=0;
1371 D_S[d].b4=0;
1372 D_S[d].f_drv_error=0;
1373 for (i=0;i<10;i++) sprintf(&msgbuf[i*3]," %02X",drvcmd[i]);
1374 msgbuf[i*3]=0;
1375 msg(DBG_CMD,"cmd_out_T:%s\n",msgbuf);
1376
1377 OUT(CDo_sel_i_d,0);
1378 OUT(CDo_enable,D_S[d].drv_sel);
1379 i=inb(CDi_status);
1380 do_16bit=0;
1381 if ((f_16bit)&&(!(i&0x80)))
1382 {
1383 do_16bit=1;
1384 msg(DBG_TEA,"cmd_out_T: do_16bit set.\n");
1385 }
1386 if (!(i&s_not_result_ready))
1387 do
1388 {
1389 j=inb(CDi_info);
1390 i=inb(CDi_status);
1391 sbp_sleep(0);
1392 msg(DBG_TEA,"cmd_out_T: spurious !s_not_result_ready. (%02X)\n", j);
1393 }
1394 while (!(i&s_not_result_ready));
1395 save_flags(flags); cli();
1396 for (i=0;i<10;i++) OUT(CDo_command,drvcmd[i]);
1397 restore_flags(flags);
1398 for (ntries=CMDT_TRIES;ntries>0;ntries--)
1399 {
1400 if (drvcmd[0]==CMDT_READ_VER) sbp_sleep(HZ);
1401#if 01
1402 OUT(CDo_sel_i_d,1);
1403#endif
1404 if (teac==2)
1405 {
1406 if ((i=CDi_stat_loop_T()) == -1) break;
1407 }
1408 else
1409 {
1410#if 0
1411 OUT(CDo_sel_i_d,1);
1412#endif
1413 i=inb(CDi_status);
1414 }
1415 if (!(i&s_not_data_ready))
1416 {
1417 OUT(CDo_sel_i_d,1);
1418 if (drvcmd[0]==CMDT_READ) return (0);
1419 if (drvcmd[0]==CMDT_DISKINFO)
1420 {
1421 l=0;
1422 do
1423 {
1424 if (do_16bit)
1425 {
1426 i=inw(CDi_data);
1427 infobuf[l++]=i&0x0ff;
1428 infobuf[l++]=i>>8;
1429#if TEST_FALSE_FF
1430 if ((l==2)&&(infobuf[0]==0x0ff))
1431 {
1432 infobuf[0]=infobuf[1];
1433 l=1;
1434 msg(DBG_TEA,"cmd_out_T: do_16bit: false first byte!\n");
1435 }
1436#endif
1437 }
1438 else infobuf[l++]=inb(CDi_data);
1439 i=inb(CDi_status);
1440 }
1441 while (!(i&s_not_data_ready));
1442 for (j=0;j<l;j++) sprintf(&msgbuf[j*3]," %02X",infobuf[j]);
1443 msgbuf[j*3]=0;
1444 msg(DBG_CMD,"cmd_out_T data response:%s\n", msgbuf);
1445 }
1446 else
1447 {
1448 msg(DBG_TEA,"cmd_out_T: data response with cmd_%02X!\n",
1449 drvcmd[0]);
1450 j=0;
1451 do
1452 {
1453 if (do_16bit) i=inw(CDi_data);
1454 else i=inb(CDi_data);
1455 j++;
1456 i=inb(CDi_status);
1457 }
1458 while (!(i&s_not_data_ready));
1459 msg(DBG_TEA,"cmd_out_T: data response: discarded %d bytes/words.\n", j);
1460 fatal_err++;
1461 }
1462 }
1463 i=inb(CDi_status);
1464 if (!(i&s_not_result_ready))
1465 {
1466 OUT(CDo_sel_i_d,0);
1467 if (drvcmd[0]==CMDT_DISKINFO) m=l;
1468 else m=0;
1469 do
1470 {
1471 infobuf[m++]=inb(CDi_info);
1472 i=inb(CDi_status);
1473 }
1474 while (!(i&s_not_result_ready));
1475 for (j=0;j<m;j++) sprintf(&msgbuf[j*3]," %02X",infobuf[j]);
1476 msgbuf[j*3]=0;
1477 msg(DBG_CMD,"cmd_out_T info response:%s\n", msgbuf);
1478 if (drvcmd[0]==CMDT_DISKINFO)
1479 {
1480 infobuf[0]=infobuf[l];
1481 if (infobuf[0]!=0x02) return (l);
1482 }
1483 else if (infobuf[0]!=0x02) return (m);
1484 do
1485 {
1486 ++recursion;
1487 if (recursion>1) msg(DBG_TEA,"cmd_out_T READ_ERR recursion (%02X): %d !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n", drvcmd[0], recursion);
1488 clr_cmdbuf();
1489 drvcmd[0]=CMDT_READ_ERR;
1490 j=cmd_out_T();
1491 --recursion;
1492 sbp_sleep(1);
1493 }
1494 while (j<0);
1495 D_S[d].error_state=infobuf[2];
1496 D_S[d].b3=infobuf[3];
1497 D_S[d].b4=infobuf[4];
1498 if (D_S[d].f_drv_error)
1499 {
1500 D_S[d].f_drv_error=0;
1501 cc_DriveReset();
1502 D_S[d].error_state=2;
1503 }
1504 return (-D_S[d].error_state-400);
1505 }
1506 if (drvcmd[0]==CMDT_READ) return (0);
1507 if ((teac==0)||(ntries<(CMDT_TRIES-5))) sbp_sleep(HZ/10);
1508 else sbp_sleep(HZ/100);
1509 if (ntries>(CMDT_TRIES-50)) continue;
1510 msg(DBG_TEA,"cmd_out_T: next CMDT_TRIES (%02X): %d.\n", drvcmd[0], ntries-1);
1511 }
1512 D_S[d].f_drv_error=1;
1513 cc_DriveReset();
1514 D_S[d].error_state=2;
1515 return (-99);
1516}
1517
1518static int cmd_out(void)
1519{
1520 int i=0;
1521
1522 if (famT_drive) return(cmd_out_T());
1523
1524 if (flags_cmd_out&f_putcmd)
1525 {
1526 unsigned long flags;
1527 for (i=0;i<7;i++)
1528 sprintf(&msgbuf[i*3], " %02X", drvcmd[i]);
1529 msgbuf[i*3]=0;
1530 msg(DBG_CMD,"cmd_out:%s\n", msgbuf);
1531 save_flags(flags); cli();
1532 for (i=0;i<7;i++) OUT(CDo_command,drvcmd[i]);
1533 restore_flags(flags);
1534 }
1535 if (response_count!=0)
1536 {
1537 if (cmd_type!=0)
1538 {
1539 if (sbpro_type==1) OUT(CDo_sel_i_d,1);
1540 msg(DBG_INF,"misleaded to try ResponseData.\n");
1541 if (sbpro_type==1) OUT(CDo_sel_i_d,0);
1542 return (-22);
1543 }
1544 else i=ResponseInfo();
1545 if (i<0) return (i);
1546 }
1547 if (D_S[d].in_SpinUp) msg(DBG_SPI,"in_SpinUp: to CDi_stat_loop.\n");
1548 if (flags_cmd_out&f_lopsta)
1549 {
1550 i=CDi_stat_loop();
1551 if ((i<0)||!(i&s_attention)) return (-8);
1552 }
1553 if (!(flags_cmd_out&f_getsta)) goto LOC_229;
1554
1555 LOC_228:
1556 if (D_S[d].in_SpinUp) msg(DBG_SPI,"in_SpinUp: to cc_ReadStatus.\n");
1557 cc_ReadStatus();
1558
1559 LOC_229:
1560 if (flags_cmd_out&f_ResponseStatus)
1561 {
1562 if (D_S[d].in_SpinUp) msg(DBG_SPI,"in_SpinUp: to ResponseStatus.\n");
1563 i=ResponseStatus();
1564
1565 if (i<0) return (i);
1566 if (flags_cmd_out&(f_bit1|f_wait_if_busy))
1567 {
1568 if (!st_check)
1569 {
1570 if ((flags_cmd_out&f_bit1)&&(i&p_success)) goto LOC_232;
1571 if ((!(flags_cmd_out&f_wait_if_busy))||(!st_busy)) goto LOC_228;
1572 }
1573 }
1574 }
1575 LOC_232:
1576 if (!(flags_cmd_out&f_obey_p_check)) return (0);
1577 if (!st_check) return (0);
1578 if (D_S[d].in_SpinUp) msg(DBG_SPI,"in_SpinUp: to cc_ReadError.\n");
1579 i=cc_ReadError();
1580 if (D_S[d].in_SpinUp) msg(DBG_SPI,"in_SpinUp: to cmd_out OK.\n");
1581 msg(DBG_000,"cmd_out: cc_ReadError=%d\n", i);
1582 return (i);
1583}
1584
1585static int cc_Seek(u_int pos, char f_blk_msf)
1586{
1587 int i;
1588
1589 clr_cmdbuf();
1590 if (f_blk_msf>1) return (-3);
1591 if (fam0V_drive)
1592 {
1593 drvcmd[0]=CMD0_SEEK;
1594 if (f_blk_msf==1) pos=msf2blk(pos);
1595 drvcmd[2]=(pos>>16)&0x00FF;
1596 drvcmd[3]=(pos>>8)&0x00FF;
1597 drvcmd[4]=pos&0x00FF;
1598 if (fam0_drive)
1599 flags_cmd_out = f_putcmd | f_respo2 | f_lopsta | f_getsta |
1600 f_ResponseStatus | f_obey_p_check | f_bit1;
1601 else
1602 flags_cmd_out = f_putcmd;
1603 }
1604 else if (fam1L_drive)
1605 {
1606 drvcmd[0]=CMD1_SEEK;
1607 if (f_blk_msf==0) pos=blk2msf(pos);
1608 drvcmd[1]=(pos>>16)&0x00FF;
1609 drvcmd[2]=(pos>>8)&0x00FF;
1610 drvcmd[3]=pos&0x00FF;
1611 if (famL_drive)
1612 flags_cmd_out=f_putcmd|f_respo2|f_lopsta|f_getsta|f_ResponseStatus|f_obey_p_check|f_bit1;
1613 else
1614 flags_cmd_out=f_putcmd|f_respo2|f_ResponseStatus|f_obey_p_check;
1615 }
1616 else if (fam2_drive)
1617 {
1618 drvcmd[0]=CMD2_SEEK;
1619 if (f_blk_msf==0) pos=blk2msf(pos);
1620 drvcmd[2]=(pos>>24)&0x00FF;
1621 drvcmd[3]=(pos>>16)&0x00FF;
1622 drvcmd[4]=(pos>>8)&0x00FF;
1623 drvcmd[5]=pos&0x00FF;
1624 flags_cmd_out=f_putcmd|f_ResponseStatus;
1625 }
1626 else if (famT_drive)
1627 {
1628 drvcmd[0]=CMDT_SEEK;
1629 if (f_blk_msf==1) pos=msf2blk(pos);
1630 drvcmd[2]=(pos>>24)&0x00FF;
1631 drvcmd[3]=(pos>>16)&0x00FF;
1632 drvcmd[4]=(pos>>8)&0x00FF;
1633 drvcmd[5]=pos&0x00FF;
1634 D_S[d].n_bytes=1;
1635 }
1636 response_count=0;
1637 i=cmd_out();
1638 return (i);
1639}
1640
1641static int cc_SpinUp(void)
1642{
1643 int i;
1644
1645 msg(DBG_SPI,"SpinUp.\n");
1646 D_S[d].in_SpinUp = 1;
1647 clr_cmdbuf();
1648 if (fam0LV_drive)
1649 {
1650 drvcmd[0]=CMD0_SPINUP;
1651 if (fam0L_drive)
1652 flags_cmd_out=f_putcmd|f_respo2|f_lopsta|f_getsta|
1653 f_ResponseStatus|f_obey_p_check|f_bit1;
1654 else
1655 flags_cmd_out=f_putcmd;
1656 }
1657 else if (fam1_drive)
1658 {
1659 drvcmd[0]=CMD1_SPINUP;
1660 flags_cmd_out=f_putcmd|f_respo2|f_ResponseStatus|f_obey_p_check;
1661 }
1662 else if (fam2_drive)
1663 {
1664 drvcmd[0]=CMD2_TRAY_CTL;
1665 drvcmd[4]=0x01;
1666 flags_cmd_out=f_putcmd|f_respo2|f_ResponseStatus|f_obey_p_check;
1667 }
1668 else if (famT_drive)
1669 {
1670 drvcmd[0]=CMDT_TRAY_CTL;
1671 drvcmd[4]=0x03;
1672 }
1673 response_count=0;
1674 i=cmd_out();
1675 D_S[d].in_SpinUp = 0;
1676 return (i);
1677}
1678
1679static int cc_SpinDown(void)
1680{
1681 int i;
1682
1683 if (fam0_drive) return (0);
1684 clr_cmdbuf();
1685 response_count=0;
1686 if (fam1_drive)
1687 {
1688 drvcmd[0]=CMD1_SPINDOWN;
1689 flags_cmd_out=f_putcmd|f_respo2|f_ResponseStatus|f_obey_p_check;
1690 }
1691 else if (fam2_drive)
1692 {
1693 drvcmd[0]=CMD2_TRAY_CTL;
1694 drvcmd[4]=0x02;
1695 flags_cmd_out=f_putcmd|f_ResponseStatus;
1696 }
1697 else if (famL_drive)
1698 {
1699 drvcmd[0]=CMDL_SPINDOWN;
1700 drvcmd[1]=1;
1701 flags_cmd_out=f_putcmd|f_respo2|f_lopsta|f_getsta|f_ResponseStatus|f_obey_p_check|f_bit1;
1702 }
1703 else if (famV_drive)
1704 {
1705 drvcmd[0]=CMDV_SPINDOWN;
1706 flags_cmd_out=f_putcmd;
1707 }
1708 else if (famT_drive)
1709 {
1710 drvcmd[0]=CMDT_TRAY_CTL;
1711 drvcmd[4]=0x02;
1712 }
1713 i=cmd_out();
1714 return (i);
1715}
1716
1717static int cc_get_mode_T(void)
1718{
1719 int i;
1720
1721 clr_cmdbuf();
1722 response_count=10;
1723 drvcmd[0]=CMDT_GETMODE;
1724 drvcmd[4]=response_count;
1725 i=cmd_out_T();
1726 return (i);
1727}
1728
1729static int cc_set_mode_T(void)
1730{
1731 int i;
1732
1733 clr_cmdbuf();
1734 response_count=1;
1735 drvcmd[0]=CMDT_SETMODE;
1736 drvcmd[1]=D_S[d].speed_byte;
1737 drvcmd[2]=D_S[d].frmsiz>>8;
1738 drvcmd[3]=D_S[d].frmsiz&0x0FF;
1739 drvcmd[4]=D_S[d].f_XA;
1740 drvcmd[5]=D_S[d].type_byte;
1741 drvcmd[6]=D_S[d].mode_xb_6;
1742 drvcmd[7]=D_S[d].mode_yb_7|D_S[d].volume_control;
1743 drvcmd[8]=D_S[d].mode_xb_8;
1744 drvcmd[9]=D_S[d].delay;
1745 i=cmd_out_T();
1746 return (i);
1747}
1748
1749static int cc_prep_mode_T(void)
1750{
1751 int i, j;
1752
1753 i=cc_get_mode_T();
1754 if (i<0) return (i);
1755 for (i=0;i<10;i++)
1756 sprintf(&msgbuf[i*3], " %02X", infobuf[i]);
1757 msgbuf[i*3]=0;
1758 msg(DBG_TEA,"CMDT_GETMODE:%s\n", msgbuf);
1759 D_S[d].speed_byte=0x02;
1760 D_S[d].frmsiz=make16(infobuf[2],infobuf[3]);
1761 D_S[d].f_XA=infobuf[4];
1762 if (D_S[d].f_XA==0) D_S[d].type_byte=0;
1763 else D_S[d].type_byte=1;
1764 D_S[d].mode_xb_6=infobuf[6];
1765 D_S[d].mode_yb_7=1;
1766 D_S[d].mode_xb_8=infobuf[8];
1767 D_S[d].delay=0;
1768 j=cc_set_mode_T();
1769 i=cc_get_mode_T();
1770 for (i=0;i<10;i++)
1771 sprintf(&msgbuf[i*3], " %02X", infobuf[i]);
1772 msgbuf[i*3]=0;
1773 msg(DBG_TEA,"CMDT_GETMODE:%s\n", msgbuf);
1774 return (j);
1775}
1776
1777static int cc_SetSpeed(u_char speed, u_char x1, u_char x2)
1778{
1779 int i;
1780
1781 if (fam0LV_drive) return (0);
1782 clr_cmdbuf();
1783 response_count=0;
1784 if (fam1_drive)
1785 {
1786 drvcmd[0]=CMD1_SETMODE;
1787 drvcmd[1]=0x03;
1788 drvcmd[2]=speed;
1789 drvcmd[3]=x1;
1790 drvcmd[4]=x2;
1791 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
1792 }
1793 else if (fam2_drive)
1794 {
1795 drvcmd[0]=CMD2_SETSPEED;
1796 if (speed&speed_auto)
1797 {
1798 drvcmd[2]=0xFF;
1799 drvcmd[3]=0xFF;
1800 }
1801 else
1802 {
1803 drvcmd[2]=0;
1804 drvcmd[3]=150;
1805 }
1806 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
1807 }
1808 else if (famT_drive)
1809 {
1810 return (0);
1811 }
1812 i=cmd_out();
1813 return (i);
1814}
1815
1816static int cc_SetVolume(void)
1817{
1818 int i;
1819 u_char channel0,channel1,volume0,volume1;
1820 u_char control0,value0,control1,value1;
1821
1822 D_S[d].diskstate_flags &= ~volume_bit;
1823 clr_cmdbuf();
1824 channel0=D_S[d].vol_chan0;
1825 volume0=D_S[d].vol_ctrl0;
1826 channel1=control1=D_S[d].vol_chan1;
1827 volume1=value1=D_S[d].vol_ctrl1;
1828 control0=value0=0;
1829
1830 if (famV_drive) return (0);
1831
1832 if (((D_S[d].drv_options&audio_mono)!=0)&&(D_S[d].drv_type>=drv_211))
1833 {
1834 if ((volume0!=0)&&(volume1==0))
1835 {
1836 volume1=volume0;
1837 channel1=channel0;
1838 }
1839 else if ((volume0==0)&&(volume1!=0))
1840 {
1841 volume0=volume1;
1842 channel0=channel1;
1843 }
1844 }
1845 if (channel0>1)
1846 {
1847 channel0=0;
1848 volume0=0;
1849 }
1850 if (channel1>1)
1851 {
1852 channel1=1;
1853 volume1=0;
1854 }
1855
1856 if (fam1_drive)
1857 {
1858 control0=channel0+1;
1859 control1=channel1+1;
1860 value0=(volume0>volume1)?volume0:volume1;
1861 value1=value0;
1862 if (volume0==0) control0=0;
1863 if (volume1==0) control1=0;
1864 drvcmd[0]=CMD1_SETMODE;
1865 drvcmd[1]=0x05;
1866 drvcmd[3]=control0;
1867 drvcmd[4]=value0;
1868 drvcmd[5]=control1;
1869 drvcmd[6]=value1;
1870 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
1871 }
1872 else if (fam2_drive)
1873 {
1874 control0=channel0+1;
1875 control1=channel1+1;
1876 value0=(volume0>volume1)?volume0:volume1;
1877 value1=value0;
1878 if (volume0==0) control0=0;
1879 if (volume1==0) control1=0;
1880 drvcmd[0]=CMD2_SETMODE;
1881 drvcmd[1]=0x0E;
1882 drvcmd[3]=control0;
1883 drvcmd[4]=value0;
1884 drvcmd[5]=control1;
1885 drvcmd[6]=value1;
1886 flags_cmd_out=f_putcmd|f_ResponseStatus;
1887 }
1888 else if (famL_drive)
1889 {
1890 if ((volume0==0)||(channel0!=0)) control0 |= 0x80;
1891 if ((volume1==0)||(channel1!=1)) control0 |= 0x40;
1892 if (volume0|volume1) value0=0x80;
1893 drvcmd[0]=CMDL_SETMODE;
1894 drvcmd[1]=0x03;
1895 drvcmd[4]=control0;
1896 drvcmd[5]=value0;
1897 flags_cmd_out=f_putcmd|f_lopsta|f_getsta|f_ResponseStatus|f_obey_p_check|f_bit1;
1898 }
1899 else if (fam0_drive)
1900 {
1901 if (D_S[d].drv_type>=drv_300)
1902 {
1903 control0=volume0&0xFC;
1904 value0=volume1&0xFC;
1905 if ((volume0!=0)&&(volume0<4)) control0 |= 0x04;
1906 if ((volume1!=0)&&(volume1<4)) value0 |= 0x04;
1907 if (channel0!=0) control0 |= 0x01;
1908 if (channel1==1) value0 |= 0x01;
1909 }
1910 else
1911 {
1912 value0=(volume0>volume1)?volume0:volume1;
1913 if (D_S[d].drv_type<drv_211)
1914 {
1915 if (channel0!=0)
1916 {
1917 i=channel1;
1918 channel1=channel0;
1919 channel0=i;
1920 i=volume1;
1921 volume1=volume0;
1922 volume0=i;
1923 }
1924 if (channel0==channel1)
1925 {
1926 if (channel0==0)
1927 {
1928 channel1=1;
1929 volume1=0;
1930 volume0=value0;
1931 }
1932 else
1933 {
1934 channel0=0;
1935 volume0=0;
1936 volume1=value0;
1937 }
1938 }
1939 }
1940
1941 if ((volume0!=0)&&(volume1!=0))
1942 {
1943 if (volume0==0xFF) volume1=0xFF;
1944 else if (volume1==0xFF) volume0=0xFF;
1945 }
1946 else if (D_S[d].drv_type<drv_201) volume0=volume1=value0;
1947
1948 if (D_S[d].drv_type>=drv_201)
1949 {
1950 if (volume0==0) control0 |= 0x80;
1951 if (volume1==0) control0 |= 0x40;
1952 }
1953 if (D_S[d].drv_type>=drv_211)
1954 {
1955 if (channel0!=0) control0 |= 0x20;
1956 if (channel1!=1) control0 |= 0x10;
1957 }
1958 }
1959 drvcmd[0]=CMD0_SETMODE;
1960 drvcmd[1]=0x83;
1961 drvcmd[4]=control0;
1962 drvcmd[5]=value0;
1963 flags_cmd_out=f_putcmd|f_getsta|f_ResponseStatus|f_obey_p_check;
1964 }
1965 else if (famT_drive)
1966 {
1967 D_S[d].volume_control=0;
1968 if (!volume0) D_S[d].volume_control|=0x10;
1969 if (!volume1) D_S[d].volume_control|=0x20;
1970 i=cc_prep_mode_T();
1971 if (i<0) return (i);
1972 }
1973 if (!famT_drive)
1974 {
1975 response_count=0;
1976 i=cmd_out();
1977 if (i<0) return (i);
1978 }
1979 D_S[d].diskstate_flags |= volume_bit;
1980 return (0);
1981}
1982
1983static int GetStatus(void)
1984{
1985 int i;
1986
1987 if (famT_drive) return (0);
1988 flags_cmd_out=f_getsta|f_ResponseStatus|f_obey_p_check;
1989 response_count=0;
1990 cmd_type=0;
1991 i=cmd_out();
1992 return (i);
1993}
1994
1995static int cc_DriveReset(void)
1996{
1997 int i;
1998
1999 msg(DBG_RES,"cc_DriveReset called.\n");
2000 clr_cmdbuf();
2001 response_count=0;
2002 if (fam0LV_drive) OUT(CDo_reset,0x00);
2003 else if (fam1_drive)
2004 {
2005 drvcmd[0]=CMD1_RESET;
2006 flags_cmd_out=f_putcmd;
2007 i=cmd_out();
2008 }
2009 else if (fam2_drive)
2010 {
2011 drvcmd[0]=CMD2_RESET;
2012 flags_cmd_out=f_putcmd;
2013 i=cmd_out();
2014 OUT(CDo_reset,0x00);
2015 }
2016 else if (famT_drive)
2017 {
2018 OUT(CDo_sel_i_d,0);
2019 OUT(CDo_enable,D_S[d].drv_sel);
2020 OUT(CDo_command,CMDT_RESET);
2021 for (i=1;i<10;i++) OUT(CDo_command,0);
2022 }
2023 if (fam0LV_drive) sbp_sleep(5*HZ);
2024 else sbp_sleep(1*HZ);
2025#if 1
2026 if (famT_drive)
2027 {
2028 msg(DBG_TEA, "================CMDT_RESET given=================.\n");
2029 sbp_sleep(3*HZ);
2030 }
2031#endif
2032 flush_status();
2033 i=GetStatus();
2034 if (i<0) return i;
2035 if (!famT_drive)
2036 if (D_S[d].error_byte!=aud_12) return -501;
2037 return (0);
2038}
2039
2040
2041static int SetSpeed(void)
2042{
2043 int i, speed;
2044
2045 if (!(D_S[d].drv_options&(speed_auto|speed_300|speed_150))) return (0);
2046 speed=speed_auto;
2047 if (!(D_S[d].drv_options&speed_auto))
2048 {
2049 speed |= speed_300;
2050 if (!(D_S[d].drv_options&speed_300)) speed=0;
2051 }
2052 i=cc_SetSpeed(speed,0,0);
2053 return (i);
2054}
2055
2056static void switch_drive(int i);
2057
2058static int sbpcd_select_speed(struct cdrom_device_info *cdi, int speed)
2059{
2060 int i = MINOR(cdi->dev);
2061
2062 if (i != d)
2063 switch_drive(i);
2064
2065 return cc_SetSpeed(speed == 2 ? speed_300 : speed_150, 0, 0);
2066}
2067
2068
2069static int DriveReset(void)
2070{
2071 int i;
2072
2073 i=cc_DriveReset();
2074 if (i<0) return (-22);
2075 do
2076 {
2077 i=GetStatus();
2078 if ((i<0)&&(i!=-ERR_DISKCHANGE)) {
2079 return (-2);
2080 }
2081 if (!st_caddy_in) break;
2082 sbp_sleep(1);
2083 }
2084 while (!st_diskok);
2085#if 000
2086 D_S[d].CD_changed=1;
2087#endif
2088 if ((st_door_closed) && (st_caddy_in))
2089 {
2090 i=DiskInfo();
2091 if (i<0) return (-23);
2092 }
2093 return (0);
2094}
2095
2096static int sbpcd_reset(struct cdrom_device_info *cdi)
2097{
2098 int i = MINOR(cdi->dev);
2099
2100 if (i != d)
2101 switch_drive(i);
2102
2103 return DriveReset();
2104}
2105
2106
2107static int cc_PlayAudio(int pos_audio_start,int pos_audio_end)
2108{
2109 int i, j, n;
2110
2111 if (D_S[d].audio_state==audio_playing) return (-EINVAL);
2112 clr_cmdbuf();
2113 response_count=0;
2114 if (famLV_drive)
2115 {
2116 drvcmd[0]=CMDL_PLAY;
2117 i=msf2blk(pos_audio_start);
2118 n=msf2blk(pos_audio_end)+1-i;
2119 drvcmd[1]=(i>>16)&0x00FF;
2120 drvcmd[2]=(i>>8)&0x00FF;
2121 drvcmd[3]=i&0x00FF;
2122 drvcmd[4]=(n>>16)&0x00FF;
2123 drvcmd[5]=(n>>8)&0x00FF;
2124 drvcmd[6]=n&0x00FF;
2125 if (famL_drive)
2126 flags_cmd_out = f_putcmd | f_respo2 | f_lopsta | f_getsta |
2127 f_ResponseStatus | f_obey_p_check | f_wait_if_busy;
2128 else
2129 flags_cmd_out = f_putcmd;
2130 }
2131 else
2132 {
2133 j=1;
2134 if (fam1_drive)
2135 {
2136 drvcmd[0]=CMD1_PLAY_MSF;
2137 flags_cmd_out = f_putcmd | f_respo2 | f_ResponseStatus |
2138 f_obey_p_check | f_wait_if_busy;
2139 }
2140 else if (fam2_drive)
2141 {
2142 drvcmd[0]=CMD2_PLAY_MSF;
2143 flags_cmd_out = f_putcmd | f_ResponseStatus | f_obey_p_check;
2144 }
2145 else if (famT_drive)
2146 {
2147 drvcmd[0]=CMDT_PLAY_MSF;
2148 j=3;
2149 response_count=1;
2150 }
2151 else if (fam0_drive)
2152 {
2153 drvcmd[0]=CMD0_PLAY_MSF;
2154 flags_cmd_out = f_putcmd | f_respo2 | f_lopsta | f_getsta |
2155 f_ResponseStatus | f_obey_p_check | f_wait_if_busy;
2156 }
2157 drvcmd[j]=(pos_audio_start>>16)&0x00FF;
2158 drvcmd[j+1]=(pos_audio_start>>8)&0x00FF;
2159 drvcmd[j+2]=pos_audio_start&0x00FF;
2160 drvcmd[j+3]=(pos_audio_end>>16)&0x00FF;
2161 drvcmd[j+4]=(pos_audio_end>>8)&0x00FF;
2162 drvcmd[j+5]=pos_audio_end&0x00FF;
2163 }
2164 i=cmd_out();
2165 return (i);
2166}
2167
2168static int cc_Pause_Resume(int pau_res)
2169{
2170 int i;
2171
2172 clr_cmdbuf();
2173 response_count=0;
2174 if (fam1_drive)
2175 {
2176 drvcmd[0]=CMD1_PAU_RES;
2177 if (pau_res!=1) drvcmd[1]=0x80;
2178 flags_cmd_out=f_putcmd|f_respo2|f_ResponseStatus|f_obey_p_check;
2179 }
2180 else if (fam2_drive)
2181 {
2182 drvcmd[0]=CMD2_PAU_RES;
2183 if (pau_res!=1) drvcmd[2]=0x01;
2184 flags_cmd_out=f_putcmd|f_ResponseStatus;
2185 }
2186 else if (fam0LV_drive)
2187 {
2188 drvcmd[0]=CMD0_PAU_RES;
2189 if (pau_res!=1) drvcmd[1]=0x80;
2190 if (famL_drive)
2191 flags_cmd_out=f_putcmd|f_respo2|f_lopsta|f_getsta|f_ResponseStatus|
2192 f_obey_p_check|f_bit1;
2193 else if (famV_drive)
2194 flags_cmd_out=f_putcmd;
2195 else
2196 flags_cmd_out=f_putcmd|f_respo2|f_lopsta|f_getsta|f_ResponseStatus|
2197 f_obey_p_check;
2198 }
2199 else if (famT_drive)
2200 {
2201 if (pau_res==3) return (cc_PlayAudio(D_S[d].pos_audio_start,D_S[d].pos_audio_end));
2202 else if (pau_res==1) drvcmd[0]=CMDT_PAUSE;
2203 else return (-56);
2204 }
2205 i=cmd_out();
2206 return (i);
2207}
2208
2209static int cc_LockDoor(char lock)
2210{
2211 int i;
2212
2213 if (fam0_drive) return (0);
2214 msg(DBG_LCK,"cc_LockDoor: %d (drive %d)\n", lock, d);
2215 msg(DBG_LCS,"p_door_locked bit %d before\n", st_door_locked);
2216 clr_cmdbuf();
2217 response_count=0;
2218 if (fam1_drive)
2219 {
2220 drvcmd[0]=CMD1_LOCK_CTL;
2221 if (lock==1) drvcmd[1]=0x01;
2222 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
2223 }
2224 else if (fam2_drive)
2225 {
2226 drvcmd[0]=CMD2_LOCK_CTL;
2227 if (lock==1) drvcmd[4]=0x01;
2228 flags_cmd_out=f_putcmd|f_ResponseStatus;
2229 }
2230 else if (famLV_drive)
2231 {
2232 drvcmd[0]=CMDL_LOCK_CTL;
2233 if (lock==1) drvcmd[1]=0x01;
2234 if (famL_drive)
2235 flags_cmd_out=f_putcmd|f_respo2|f_lopsta|f_getsta|f_ResponseStatus|f_obey_p_check|f_bit1;
2236 else
2237 flags_cmd_out=f_putcmd;
2238 }
2239 else if (famT_drive)
2240 {
2241 drvcmd[0]=CMDT_LOCK_CTL;
2242 if (lock==1) drvcmd[4]=0x01;
2243 }
2244 i=cmd_out();
2245 msg(DBG_LCS,"p_door_locked bit %d after\n", st_door_locked);
2246 return (i);
2247}
2248
2249
2250static int UnLockDoor(void)
2251{
2252 int i,j;
2253
2254 j=20;
2255 do
2256 {
2257 i=cc_LockDoor(0);
2258 --j;
2259 sbp_sleep(1);
2260 }
2261 while ((i<0)&&(j));
2262 if (i<0)
2263 {
2264 cc_DriveReset();
2265 return -84;
2266 }
2267 return (0);
2268}
2269
2270static int LockDoor(void)
2271{
2272 int i,j;
2273
2274 j=20;
2275 do
2276 {
2277 i=cc_LockDoor(1);
2278 --j;
2279 sbp_sleep(1);
2280 }
2281 while ((i<0)&&(j));
2282 if (j==0)
2283 {
2284 cc_DriveReset();
2285 j=20;
2286 do
2287 {
2288 i=cc_LockDoor(1);
2289 --j;
2290 sbp_sleep(1);
2291 }
2292 while ((i<0)&&(j));
2293 }
2294 return (i);
2295}
2296
2297static int sbpcd_lock_door(struct cdrom_device_info *cdi, int lock)
2298{
2299 return lock ? LockDoor() : UnLockDoor();
2300}
2301
2302
2303static int cc_CloseTray(void)
2304{
2305 int i;
2306
2307 if (fam0_drive) return (0);
2308 msg(DBG_LCK,"cc_CloseTray (drive %d)\n", d);
2309 msg(DBG_LCS,"p_door_closed bit %d before\n", st_door_closed);
2310
2311 clr_cmdbuf();
2312 response_count=0;
2313 if (fam1_drive)
2314 {
2315 drvcmd[0]=CMD1_TRAY_CTL;
2316 flags_cmd_out=f_putcmd|f_respo2|f_ResponseStatus|f_obey_p_check;
2317 }
2318 else if (fam2_drive)
2319 {
2320 drvcmd[0]=CMD2_TRAY_CTL;
2321 drvcmd[1]=0x01;
2322 drvcmd[4]=0x03;
2323 flags_cmd_out=f_putcmd|f_ResponseStatus;
2324 }
2325 else if (famLV_drive)
2326 {
2327 drvcmd[0]=CMDL_TRAY_CTL;
2328 if (famLV_drive)
2329 flags_cmd_out=f_putcmd|f_respo2|f_lopsta|f_getsta|
2330 f_ResponseStatus|f_obey_p_check|f_bit1;
2331 else
2332 flags_cmd_out=f_putcmd;
2333 }
2334 else if (famT_drive)
2335 {
2336 drvcmd[0]=CMDT_TRAY_CTL;
2337 drvcmd[4]=0x03;
2338 }
2339 i=cmd_out();
2340 msg(DBG_LCS,"p_door_closed bit %d after\n", st_door_closed);
2341
2342 i=cc_ReadError();
2343 flags_cmd_out |= f_respo2;
2344 cc_ReadStatus();
2345 i=ResponseStatus();
2346 if (famT_drive&&(i<0))
2347 {
2348 cc_DriveReset();
2349 i=ResponseStatus();
2350#if 0
2351 sbp_sleep(HZ);
2352#endif
2353 i=ResponseStatus();
2354 }
2355 if (i<0)
2356 {
2357 msg(DBG_INF,"sbpcd cc_CloseTray: ResponseStatus timed out (%d).\n",i);
2358 }
2359 if (!(famT_drive))
2360 {
2361 if (!st_spinning)
2362 {
2363 cc_SpinUp();
2364 if (st_check) i=cc_ReadError();
2365 flags_cmd_out |= f_respo2;
2366 cc_ReadStatus();
2367 i=ResponseStatus();
2368 } else {
2369 }
2370 }
2371 i=DiskInfo();
2372 return (i);
2373}
2374
2375static int sbpcd_tray_move(struct cdrom_device_info *cdi, int position)
2376{
2377 int i;
2378 int retval=0;
2379 i = MINOR(cdi->dev);
2380 switch_drive(i);
2381
2382 if(D_S[d].CD_changed != 0xFF) {
2383 D_S[d].CD_changed=0xFF;
2384 D_S[d].diskstate_flags &= ~cd_size_bit;
2385 }
2386 if (position == 1) {
2387 cc_SpinDown();
2388 } else {
2389 retval=cc_CloseTray();
2390 }
2391 return retval;
2392}
2393
2394
2395static int cc_ReadSubQ(void)
2396{
2397 int i,j;
2398
2399 D_S[d].diskstate_flags &= ~subq_bit;
2400 for (j=255;j>0;j--)
2401 {
2402 clr_cmdbuf();
2403 if (fam1_drive)
2404 {
2405 drvcmd[0]=CMD1_READSUBQ;
2406 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
2407 response_count=11;
2408 }
2409 else if (fam2_drive)
2410 {
2411 drvcmd[0]=CMD2_READSUBQ;
2412 drvcmd[1]=0x02;
2413 drvcmd[3]=0x01;
2414 flags_cmd_out=f_putcmd;
2415 response_count=10;
2416 }
2417 else if (fam0LV_drive)
2418 {
2419 drvcmd[0]=CMD0_READSUBQ;
2420 drvcmd[1]=0x02;
2421 if (famLV_drive)
2422 flags_cmd_out=f_putcmd;
2423 else
2424 flags_cmd_out=f_putcmd|f_getsta|f_ResponseStatus|f_obey_p_check;
2425 response_count=13;
2426 }
2427 else if (famT_drive)
2428 {
2429 response_count=12;
2430 drvcmd[0]=CMDT_READSUBQ;
2431 drvcmd[1]=0x02;
2432 drvcmd[2]=0x40;
2433 drvcmd[3]=0x01;
2434 drvcmd[8]=response_count;
2435 }
2436 i=cmd_out();
2437 if (i<0) return (i);
2438 for (i=0;i<response_count;i++)
2439 {
2440 sprintf(&msgbuf[i*3], " %02X", infobuf[i]);
2441 msgbuf[i*3]=0;
2442 msg(DBG_SQ1,"cc_ReadSubQ:%s\n", msgbuf);
2443 }
2444 if (famT_drive) break;
2445 if (infobuf[0]!=0) break;
2446 if ((!st_spinning) || (j==1))
2447 {
2448 D_S[d].SubQ_ctl_adr=D_S[d].SubQ_trk=D_S[d].SubQ_pnt_idx=D_S[d].SubQ_whatisthis=0;
2449 D_S[d].SubQ_run_tot=D_S[d].SubQ_run_trk=0;
2450 return (0);
2451 }
2452 }
2453 if (famT_drive) D_S[d].SubQ_ctl_adr=infobuf[1];
2454 else D_S[d].SubQ_ctl_adr=swap_nibbles(infobuf[1]);
2455 D_S[d].SubQ_trk=byt2bcd(infobuf[2]);
2456 D_S[d].SubQ_pnt_idx=byt2bcd(infobuf[3]);
2457 if (fam0LV_drive) i=5;
2458 else if (fam12_drive) i=4;
2459 else if (famT_drive) i=8;
2460 D_S[d].SubQ_run_tot=make32(make16(0,infobuf[i]),make16(infobuf[i+1],infobuf[i+2]));
2461 i=7;
2462 if (fam0LV_drive) i=9;
2463 else if (fam12_drive) i=7;
2464 else if (famT_drive) i=4;
2465 D_S[d].SubQ_run_trk=make32(make16(0,infobuf[i]),make16(infobuf[i+1],infobuf[i+2]));
2466 D_S[d].SubQ_whatisthis=infobuf[i+3];
2467 D_S[d].diskstate_flags |= subq_bit;
2468 return (0);
2469}
2470
2471static int cc_ModeSense(void)
2472{
2473 int i;
2474
2475 if (fam2_drive) return (0);
2476 if (famV_drive) return (0);
2477 D_S[d].diskstate_flags &= ~frame_size_bit;
2478 clr_cmdbuf();
2479 if (fam1_drive)
2480 {
2481 response_count=5;
2482 drvcmd[0]=CMD1_GETMODE;
2483 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
2484 }
2485 else if (fam0L_drive)
2486 {
2487 response_count=2;
2488 drvcmd[0]=CMD0_GETMODE;
2489 if (famL_drive) flags_cmd_out=f_putcmd;
2490 else flags_cmd_out=f_putcmd|f_getsta|f_ResponseStatus|f_obey_p_check;
2491 }
2492 else if (famT_drive)
2493 {
2494 response_count=10;
2495 drvcmd[0]=CMDT_GETMODE;
2496 drvcmd[4]=response_count;
2497 }
2498 i=cmd_out();
2499 if (i<0) return (i);
2500 i=0;
2501 D_S[d].sense_byte=0;
2502 if (fam1_drive) D_S[d].sense_byte=infobuf[i++];
2503 else if (famT_drive)
2504 {
2505 if (infobuf[4]==0x01) D_S[d].xa_byte=0x20;
2506 else D_S[d].xa_byte=0;
2507 i=2;
2508 }
2509 D_S[d].frame_size=make16(infobuf[i],infobuf[i+1]);
2510 for (i=0;i<response_count;i++)
2511 sprintf(&msgbuf[i*3], " %02X", infobuf[i]);
2512 msgbuf[i*3]=0;
2513 msg(DBG_XA1,"cc_ModeSense:%s\n", msgbuf);
2514
2515 D_S[d].diskstate_flags |= frame_size_bit;
2516 return (0);
2517}
2518
2519
2520static int cc_ModeSelect(int framesize)
2521{
2522 int i;
2523
2524 if (fam2_drive) return (0);
2525 if (famV_drive) return (0);
2526 D_S[d].diskstate_flags &= ~frame_size_bit;
2527 clr_cmdbuf();
2528 D_S[d].frame_size=framesize;
2529 if (framesize==CD_FRAMESIZE_RAW) D_S[d].sense_byte=0x82;
2530 else D_S[d].sense_byte=0x00;
2531
2532 msg(DBG_XA1,"cc_ModeSelect: %02X %04X\n",
2533 D_S[d].sense_byte, D_S[d].frame_size);
2534
2535 if (fam1_drive)
2536 {
2537 drvcmd[0]=CMD1_SETMODE;
2538 drvcmd[1]=0x00;
2539 drvcmd[2]=D_S[d].sense_byte;
2540 drvcmd[3]=(D_S[d].frame_size>>8)&0xFF;
2541 drvcmd[4]=D_S[d].frame_size&0xFF;
2542 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
2543 }
2544 else if (fam0L_drive)
2545 {
2546 drvcmd[0]=CMD0_SETMODE;
2547 drvcmd[1]=0x00;
2548 drvcmd[2]=(D_S[d].frame_size>>8)&0xFF;
2549 drvcmd[3]=D_S[d].frame_size&0xFF;
2550 drvcmd[4]=0x00;
2551 if(famL_drive)
2552 flags_cmd_out=f_putcmd|f_lopsta|f_getsta|f_ResponseStatus|f_obey_p_check;
2553 else
2554 flags_cmd_out=f_putcmd|f_getsta|f_ResponseStatus|f_obey_p_check;
2555 }
2556 else if (famT_drive)
2557 {
2558 return (-1);
2559 }
2560 response_count=0;
2561 i=cmd_out();
2562 if (i<0) return (i);
2563 D_S[d].diskstate_flags |= frame_size_bit;
2564 return (0);
2565}
2566
2567static int cc_GetVolume(void)
2568{
2569 int i;
2570 u_char switches;
2571 u_char chan0=0;
2572 u_char vol0=0;
2573 u_char chan1=1;
2574 u_char vol1=0;
2575
2576 if (famV_drive) return (0);
2577 D_S[d].diskstate_flags &= ~volume_bit;
2578 clr_cmdbuf();
2579 if (fam1_drive)
2580 {
2581 drvcmd[0]=CMD1_GETMODE;
2582 drvcmd[1]=0x05;
2583 response_count=5;
2584 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
2585 }
2586 else if (fam2_drive)
2587 {
2588 drvcmd[0]=CMD2_GETMODE;
2589 drvcmd[1]=0x0E;
2590 response_count=5;
2591 flags_cmd_out=f_putcmd;
2592 }
2593 else if (fam0L_drive)
2594 {
2595 drvcmd[0]=CMD0_GETMODE;
2596 drvcmd[1]=0x03;
2597 response_count=2;
2598 if(famL_drive)
2599 flags_cmd_out=f_putcmd;
2600 else
2601 flags_cmd_out=f_putcmd|f_getsta|f_ResponseStatus|f_obey_p_check;
2602 }
2603 else if (famT_drive)
2604 {
2605 i=cc_get_mode_T();
2606 if (i<0) return (i);
2607 }
2608 if (!famT_drive)
2609 {
2610 i=cmd_out();
2611 if (i<0) return (i);
2612 }
2613 if (fam1_drive)
2614 {
2615 chan0=infobuf[1]&0x0F;
2616 vol0=infobuf[2];
2617 chan1=infobuf[3]&0x0F;
2618 vol1=infobuf[4];
2619 if (chan0==0)
2620 {
2621 chan0=1;
2622 vol0=0;
2623 }
2624 if (chan1==0)
2625 {
2626 chan1=2;
2627 vol1=0;
2628 }
2629 chan0 >>= 1;
2630 chan1 >>= 1;
2631 }
2632 else if (fam2_drive)
2633 {
2634 chan0=infobuf[1];
2635 vol0=infobuf[2];
2636 chan1=infobuf[3];
2637 vol1=infobuf[4];
2638 }
2639 else if (famL_drive)
2640 {
2641 chan0=0;
2642 chan1=1;
2643 vol0=vol1=infobuf[1];
2644 switches=infobuf[0];
2645 if ((switches&0x80)!=0) chan0=1;
2646 if ((switches&0x40)!=0) chan1=0;
2647 }
2648 else if (fam0_drive)
2649 {
2650 chan0=0;
2651 chan1=1;
2652 vol0=vol1=infobuf[1];
2653 if (D_S[d].drv_type>=drv_201)
2654 {
2655 if (D_S[d].drv_type<drv_300)
2656 {
2657 switches=infobuf[0];
2658 if ((switches&0x80)!=0) vol0=0;
2659 if ((switches&0x40)!=0) vol1=0;
2660 if (D_S[d].drv_type>=drv_211)
2661 {
2662 if ((switches&0x20)!=0) chan0=1;
2663 if ((switches&0x10)!=0) chan1=0;
2664 }
2665 }
2666 else
2667 {
2668 vol0=infobuf[0];
2669 if ((vol0&0x01)!=0) chan0=1;
2670 if ((vol1&0x01)==0) chan1=0;
2671 vol0 &= 0xFC;
2672 vol1 &= 0xFC;
2673 if (vol0!=0) vol0 += 3;
2674 if (vol1!=0) vol1 += 3;
2675 }
2676 }
2677 }
2678 else if (famT_drive)
2679 {
2680 D_S[d].volume_control=infobuf[7];
2681 chan0=0;
2682 chan1=1;
2683 if (D_S[d].volume_control&0x10) vol0=0;
2684 else vol0=0xff;
2685 if (D_S[d].volume_control&0x20) vol1=0;
2686 else vol1=0xff;
2687 }
2688 D_S[d].vol_chan0=chan0;
2689 D_S[d].vol_ctrl0=vol0;
2690 D_S[d].vol_chan1=chan1;
2691 D_S[d].vol_ctrl1=vol1;
2692#if 000
2693 D_S[d].vol_chan2=2;
2694 D_S[d].vol_ctrl2=0xFF;
2695 D_S[d].vol_chan3=3;
2696 D_S[d].vol_ctrl3=0xFF;
2697#endif
2698 D_S[d].diskstate_flags |= volume_bit;
2699 return (0);
2700}
2701
2702static int cc_ReadCapacity(void)
2703{
2704 int i, j;
2705
2706 if (fam2_drive) return (0);
2707 if (famLV_drive) return (0);
2708 if (famT_drive) return (0);
2709 D_S[d].diskstate_flags &= ~cd_size_bit;
2710 for (j=3;j>0;j--)
2711 {
2712 clr_cmdbuf();
2713 if (fam1_drive)
2714 {
2715 drvcmd[0]=CMD1_CAPACITY;
2716 response_count=5;
2717 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
2718 }
2719#if 00
2720 else if (fam2_drive)
2721 {
2722 drvcmd[0]=CMD2_CAPACITY;
2723 response_count=8;
2724 flags_cmd_out=f_putcmd;
2725 }
2726#endif
2727 else if (fam0_drive)
2728 {
2729 drvcmd[0]=CMD0_CAPACITY;
2730 response_count=5;
2731 flags_cmd_out=f_putcmd|f_getsta|f_ResponseStatus|f_obey_p_check;
2732 }
2733 i=cmd_out();
2734 if (i>=0) break;
2735 msg(DBG_000,"cc_ReadCapacity: cmd_out: err %d\n", i);
2736 cc_ReadError();
2737 }
2738 if (j==0) return (i);
2739 if (fam1_drive) D_S[d].CDsize_frm=msf2blk(make32(make16(0,infobuf[0]),make16(infobuf[1],infobuf[2])))+CD_MSF_OFFSET;
2740 else if (fam0_drive) D_S[d].CDsize_frm=make32(make16(0,infobuf[0]),make16(infobuf[1],infobuf[2]));
2741#if 00
2742 else if (fam2_drive) D_S[d].CDsize_frm=make32(make16(infobuf[0],infobuf[1]),make16(infobuf[2],infobuf[3]));
2743#endif
2744 D_S[d].diskstate_flags |= cd_size_bit;
2745 msg(DBG_000,"cc_ReadCapacity: %d frames.\n", D_S[d].CDsize_frm);
2746 return (0);
2747}
2748
2749static int cc_ReadTocDescr(void)
2750{
2751 int i;
2752
2753 D_S[d].diskstate_flags &= ~toc_bit;
2754 clr_cmdbuf();
2755 if (fam1_drive)
2756 {
2757 drvcmd[0]=CMD1_DISKINFO;
2758 response_count=6;
2759 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
2760 }
2761 else if (fam0LV_drive)
2762 {
2763 drvcmd[0]=CMD0_DISKINFO;
2764 response_count=6;
2765 if(famLV_drive)
2766 flags_cmd_out=f_putcmd;
2767 else
2768 flags_cmd_out=f_putcmd|f_getsta|f_ResponseStatus|f_obey_p_check;
2769 }
2770 else if (fam2_drive)
2771 {
2772
2773 D_S[d].f_multisession=0;
2774 drvcmd[0]=CMD2_DISKINFO;
2775 drvcmd[1]=0x02;
2776 drvcmd[2]=0xAB;
2777 drvcmd[3]=0xFF;
2778 response_count=8;
2779 flags_cmd_out=f_putcmd;
2780 }
2781 else if (famT_drive)
2782 {
2783 D_S[d].f_multisession=0;
2784 response_count=12;
2785 drvcmd[0]=CMDT_DISKINFO;
2786 drvcmd[1]=0x02;
2787 drvcmd[6]=CDROM_LEADOUT;
2788 drvcmd[8]=response_count;
2789 drvcmd[9]=0x00;
2790 }
2791 i=cmd_out();
2792 if (i<0) return (i);
2793 if ((famT_drive)&&(i<response_count)) return (-100-i);
2794 if ((fam1_drive)||(fam2_drive)||(fam0LV_drive))
2795 D_S[d].xa_byte=infobuf[0];
2796 if (fam2_drive)
2797 {
2798 D_S[d].first_session=infobuf[1];
2799 D_S[d].last_session=infobuf[2];
2800 D_S[d].n_first_track=infobuf[3];
2801 D_S[d].n_last_track=infobuf[4];
2802 if (D_S[d].first_session!=D_S[d].last_session)
2803 {
2804 D_S[d].f_multisession=1;
2805 D_S[d].lba_multi=msf2blk(make32(make16(0,infobuf[5]),make16(infobuf[6],infobuf[7])));
2806 }
2807#if 0
2808 if (D_S[d].first_session!=D_S[d].last_session)
2809 {
2810 if (D_S[d].last_session<=20)
2811 zwanzig=D_S[d].last_session+1;
2812 else zwanzig=20;
2813 for (count=D_S[d].first_session;count<zwanzig;count++)
2814 {
2815 drvcmd[0]=CMD2_DISKINFO;
2816 drvcmd[1]=0x02;
2817 drvcmd[2]=0xAB;
2818 drvcmd[3]=count;
2819 response_count=8;
2820 flags_cmd_out=f_putcmd;
2821 i=cmd_out();
2822 if (i<0) return (i);
2823 D_S[d].msf_multi_n[count]=make32(make16(0,infobuf[5]),make16(infobuf[6],infobuf[7]));
2824 }
2825 D_S[d].diskstate_flags |= multisession_bit;
2826 }
2827#endif
2828 drvcmd[0]=CMD2_DISKINFO;
2829 drvcmd[1]=0x02;
2830 drvcmd[2]=0xAA;
2831 drvcmd[3]=0xFF;
2832 response_count=5;
2833 flags_cmd_out=f_putcmd;
2834 i=cmd_out();
2835 if (i<0) return (i);
2836 D_S[d].size_msf=make32(make16(0,infobuf[2]),make16(infobuf[3],infobuf[4]));
2837 D_S[d].size_blk=msf2blk(D_S[d].size_msf);
2838 D_S[d].CDsize_frm=D_S[d].size_blk+1;
2839 }
2840 else if (famT_drive)
2841 {
2842 D_S[d].size_msf=make32(make16(infobuf[8],infobuf[9]),make16(infobuf[10],infobuf[11]));
2843 D_S[d].size_blk=msf2blk(D_S[d].size_msf);
2844 D_S[d].CDsize_frm=D_S[d].size_blk+1;
2845 D_S[d].n_first_track=infobuf[2];
2846 D_S[d].n_last_track=infobuf[3];
2847 }
2848 else
2849 {
2850 D_S[d].n_first_track=infobuf[1];
2851 D_S[d].n_last_track=infobuf[2];
2852 D_S[d].size_msf=make32(make16(0,infobuf[3]),make16(infobuf[4],infobuf[5]));
2853 D_S[d].size_blk=msf2blk(D_S[d].size_msf);
2854 if (famLV_drive) D_S[d].CDsize_frm=D_S[d].size_blk+1;
2855 }
2856 D_S[d].diskstate_flags |= toc_bit;
2857 msg(DBG_TOC,"TocDesc: xa %02X firstt %02X lastt %02X size %08X firstses %02X lastsess %02X\n",
2858 D_S[d].xa_byte,
2859 D_S[d].n_first_track,
2860 D_S[d].n_last_track,
2861 D_S[d].size_msf,
2862 D_S[d].first_session,
2863 D_S[d].last_session);
2864 return (0);
2865}
2866
2867static int cc_ReadTocEntry(int num)
2868{
2869 int i;
2870
2871 clr_cmdbuf();
2872 if (fam1_drive)
2873 {
2874 drvcmd[0]=CMD1_READTOC;
2875 drvcmd[2]=num;
2876 response_count=8;
2877 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
2878 }
2879 else if (fam2_drive)
2880 {
2881
2882 drvcmd[0]=CMD2_DISKINFO;
2883 drvcmd[1]=0x02;
2884 drvcmd[2]=num;
2885 response_count=5;
2886 flags_cmd_out=f_putcmd;
2887 }
2888 else if (fam0LV_drive)
2889 {
2890 drvcmd[0]=CMD0_READTOC;
2891 drvcmd[1]=0x02;
2892 drvcmd[2]=num;
2893 response_count=8;
2894 if (famLV_drive)
2895 flags_cmd_out=f_putcmd;
2896 else
2897 flags_cmd_out=f_putcmd|f_getsta|f_ResponseStatus|f_obey_p_check;
2898 }
2899 else if (famT_drive)
2900 {
2901 response_count=12;
2902 drvcmd[0]=CMDT_DISKINFO;
2903 drvcmd[1]=0x02;
2904 drvcmd[6]=num;
2905 drvcmd[8]=response_count;
2906 drvcmd[9]=0x00;
2907 }
2908 i=cmd_out();
2909 if (i<0) return (i);
2910 if ((famT_drive)&&(i<response_count)) return (-100-i);
2911 if ((fam1_drive)||(fam0LV_drive))
2912 {
2913 D_S[d].TocEnt_nixbyte=infobuf[0];
2914 i=1;
2915 }
2916 else if (fam2_drive) i=0;
2917 else if (famT_drive) i=5;
2918 D_S[d].TocEnt_ctl_adr=swap_nibbles(infobuf[i++]);
2919 if ((fam1_drive)||(fam0L_drive))
2920 {
2921 D_S[d].TocEnt_number=infobuf[i++];
2922 D_S[d].TocEnt_format=infobuf[i];
2923 }
2924 else
2925 {
2926 D_S[d].TocEnt_number=num;
2927 D_S[d].TocEnt_format=0;
2928 }
2929 if (fam1_drive) i=4;
2930 else if (fam0LV_drive) i=5;
2931 else if (fam2_drive) i=2;
2932 else if (famT_drive) i=9;
2933 D_S[d].TocEnt_address=make32(make16(0,infobuf[i]),
2934 make16(infobuf[i+1],infobuf[i+2]));
2935 for (i=0;i<response_count;i++)
2936 sprintf(&msgbuf[i*3], " %02X", infobuf[i]);
2937 msgbuf[i*3]=0;
2938 msg(DBG_ECS,"TocEntry:%s\n", msgbuf);
2939 msg(DBG_TOC,"TocEntry: %02X %02X %02X %02X %08X\n",
2940 D_S[d].TocEnt_nixbyte, D_S[d].TocEnt_ctl_adr,
2941 D_S[d].TocEnt_number, D_S[d].TocEnt_format,
2942 D_S[d].TocEnt_address);
2943 return (0);
2944}
2945
2946static int cc_ReadPacket(void)
2947{
2948 int i;
2949
2950 clr_cmdbuf();
2951 drvcmd[0]=CMD0_PACKET;
2952 drvcmd[1]=response_count;
2953 if(famL_drive) flags_cmd_out=f_putcmd;
2954 else if (fam01_drive)
2955 flags_cmd_out=f_putcmd|f_getsta|f_ResponseStatus|f_obey_p_check;
2956 else if (fam2_drive) return (-1);
2957 else if (famT_drive)
2958 {
2959 return (-1);
2960 }
2961 i=cmd_out();
2962 return (i);
2963}
2964
2965static int convert_UPC(u_char *p)
2966{
2967 int i;
2968
2969 p++;
2970 if (fam0L_drive) p[13]=0;
2971 for (i=0;i<7;i++)
2972 {
2973 if (fam1_drive) D_S[d].UPC_buf[i]=swap_nibbles(*p++);
2974 else if (fam0L_drive)
2975 {
2976 D_S[d].UPC_buf[i]=((*p++)<<4)&0xFF;
2977 D_S[d].UPC_buf[i] |= *p++;
2978 }
2979 else if (famT_drive)
2980 {
2981 return (-1);
2982 }
2983 else
2984 {
2985 return (-1);
2986 }
2987 }
2988 D_S[d].UPC_buf[6] &= 0xF0;
2989 return (0);
2990}
2991
2992static int cc_ReadUPC(void)
2993{
2994 int i;
2995#if TEST_UPC
2996 int block, checksum;
2997#endif
2998
2999 if (fam2_drive) return (0);
3000 if (famT_drive) return (0);
3001 if (famV_drive) return (0);
3002#if 1
3003 if (fam0_drive) return (0);
3004#endif
3005
3006 D_S[d].diskstate_flags &= ~upc_bit;
3007#if TEST_UPC
3008 for (block=CD_MSF_OFFSET+1;block<CD_MSF_OFFSET+200;block++)
3009 {
3010#endif
3011 clr_cmdbuf();
3012 if (fam1_drive)
3013 {
3014 drvcmd[0]=CMD1_READ_UPC;
3015#if TEST_UPC
3016 drvcmd[1]=(block>>16)&0xFF;
3017 drvcmd[2]=(block>>8)&0xFF;
3018 drvcmd[3]=block&0xFF;
3019#endif
3020 response_count=8;
3021 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
3022 }
3023 else if (fam0L_drive)
3024 {
3025 drvcmd[0]=CMD0_READ_UPC;
3026#if TEST_UPC
3027 drvcmd[2]=(block>>16)&0xFF;
3028 drvcmd[3]=(block>>8)&0xFF;
3029 drvcmd[4]=block&0xFF;
3030#endif
3031 response_count=0;
3032 flags_cmd_out=f_putcmd|f_lopsta|f_getsta|f_ResponseStatus|f_obey_p_check|f_bit1;
3033 }
3034 else if (fam2_drive)
3035 {
3036 return (-1);
3037 }
3038 else if (famT_drive)
3039 {
3040 return (-1);
3041 }
3042 i=cmd_out();
3043 if (i<0)
3044 {
3045 msg(DBG_000,"cc_ReadUPC cmd_out: err %d\n", i);
3046 return (i);
3047 }
3048 if (fam0L_drive)
3049 {
3050 response_count=16;
3051 if (famL_drive) flags_cmd_out=f_putcmd;
3052 i=cc_ReadPacket();
3053 if (i<0)
3054 {
3055 msg(DBG_000,"cc_ReadUPC ReadPacket: err %d\n", i);
3056 return (i);
3057 }
3058 }
3059#if TEST_UPC
3060 checksum=0;
3061#endif
3062 for (i=0;i<(fam1_drive?8:16);i++)
3063 {
3064#if TEST_UPC
3065 checksum |= infobuf[i];
3066#endif
3067 sprintf(&msgbuf[i*3], " %02X", infobuf[i]);
3068 }
3069 msgbuf[i*3]=0;
3070 msg(DBG_UPC,"UPC info:%s\n", msgbuf);
3071#if TEST_UPC
3072 if ((checksum&0x7F)!=0) break;
3073 }
3074#endif
3075 D_S[d].UPC_ctl_adr=0;
3076 if (fam1_drive) i=0;
3077 else i=2;
3078 if ((infobuf[i]&0x80)!=0)
3079 {
3080 convert_UPC(&infobuf[i]);
3081 D_S[d].UPC_ctl_adr = (D_S[d].TocEnt_ctl_adr & 0xF0) | 0x02;
3082 }
3083 for (i=0;i<7;i++)
3084 sprintf(&msgbuf[i*3], " %02X", D_S[d].UPC_buf[i]);
3085 sprintf(&msgbuf[i*3], " (%02X)", D_S[d].UPC_ctl_adr);
3086 msgbuf[i*3+5]=0;
3087 msg(DBG_UPC,"UPC code:%s\n", msgbuf);
3088 D_S[d].diskstate_flags |= upc_bit;
3089 return (0);
3090}
3091
3092static int sbpcd_get_mcn(struct cdrom_device_info *cdi, struct cdrom_mcn *mcn)
3093{
3094 int i;
3095 unsigned char *mcnp = mcn->medium_catalog_number;
3096 unsigned char *resp;
3097
3098 D_S[d].diskstate_flags &= ~upc_bit;
3099 clr_cmdbuf();
3100 if (fam1_drive)
3101 {
3102 drvcmd[0]=CMD1_READ_UPC;
3103 response_count=8;
3104 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
3105 }
3106 else if (fam0L_drive)
3107 {
3108 drvcmd[0]=CMD0_READ_UPC;
3109 response_count=0;
3110 flags_cmd_out=f_putcmd|f_lopsta|f_getsta|f_ResponseStatus|f_obey_p_check|f_bit1;
3111 }
3112 else if (fam2_drive)
3113 {
3114 return (-1);
3115 }
3116 else if (famT_drive)
3117 {
3118 return (-1);
3119 }
3120 i=cmd_out();
3121 if (i<0)
3122 {
3123 msg(DBG_000,"cc_ReadUPC cmd_out: err %d\n", i);
3124 return (i);
3125 }
3126 if (fam0L_drive)
3127 {
3128 response_count=16;
3129 if (famL_drive) flags_cmd_out=f_putcmd;
3130 i=cc_ReadPacket();
3131 if (i<0)
3132 {
3133 msg(DBG_000,"cc_ReadUPC ReadPacket: err %d\n", i);
3134 return (i);
3135 }
3136 }
3137 D_S[d].UPC_ctl_adr=0;
3138 if (fam1_drive) i=0;
3139 else i=2;
3140
3141 resp = infobuf + i;
3142 if (*resp++ == 0x80) {
3143
3144 *mcnp++ = (*resp >> 4) + '0';
3145 *mcnp++ = (*resp++ & 0x0f) + '0';
3146 *mcnp++ = (*resp >> 4) + '0';
3147 *mcnp++ = (*resp++ & 0x0f) + '0';
3148 *mcnp++ = (*resp >> 4) + '0';
3149 *mcnp++ = (*resp++ & 0x0f) + '0';
3150 *mcnp++ = (*resp >> 4) + '0';
3151 *mcnp++ = (*resp++ & 0x0f) + '0';
3152 *mcnp++ = (*resp >> 4) + '0';
3153 *mcnp++ = (*resp++ & 0x0f) + '0';
3154 *mcnp++ = (*resp >> 4) + '0';
3155 *mcnp++ = (*resp++ & 0x0f) + '0';
3156 *mcnp++ = (*resp >> 4) + '0';
3157 }
3158 *mcnp = '\0';
3159
3160 D_S[d].diskstate_flags |= upc_bit;
3161 return (0);
3162}
3163
3164
3165static int cc_CheckMultiSession(void)
3166{
3167 int i;
3168
3169 if (fam2_drive) return (0);
3170 D_S[d].f_multisession=0;
3171 D_S[d].lba_multi=0;
3172 if (fam0_drive) return (0);
3173 clr_cmdbuf();
3174 if (fam1_drive)
3175 {
3176 drvcmd[0]=CMD1_MULTISESS;
3177 response_count=6;
3178 flags_cmd_out=f_putcmd|f_ResponseStatus|f_obey_p_check;
3179 i=cmd_out();
3180 if (i<0) return (i);
3181 if ((infobuf[0]&0x80)!=0)
3182 {
3183 D_S[d].f_multisession=1;
3184 D_S[d].lba_multi=msf2blk(make32(make16(0,infobuf[1]),
3185 make16(infobuf[2],infobuf[3])));
3186 }
3187 }
3188 else if (famLV_drive)
3189 {
3190 drvcmd[0]=CMDL_MULTISESS;
3191 drvcmd[1]=3;
3192 drvcmd[2]=1;
3193 response_count=8;
3194 flags_cmd_out=f_putcmd;
3195 i=cmd_out();
3196 if (i<0) return (i);
3197 D_S[d].lba_multi=msf2blk(make32(make16(0,infobuf[5]),
3198 make16(infobuf[6],infobuf[7])));
3199 }
3200 else if (famT_drive)
3201 {
3202 response_count=12;
3203 drvcmd[0]=CMDT_DISKINFO;
3204 drvcmd[1]=0x02;
3205 drvcmd[6]=0;
3206 drvcmd[8]=response_count;
3207 drvcmd[9]=0x40;
3208 i=cmd_out();
3209 if (i<0) return (i);
3210 if (i<response_count) return (-100-i);
3211 D_S[d].first_session=infobuf[2];
3212 D_S[d].last_session=infobuf[3];
3213 D_S[d].track_of_last_session=infobuf[6];
3214 if (D_S[d].first_session!=D_S[d].last_session)
3215 {
3216 D_S[d].f_multisession=1;
3217 D_S[d].lba_multi=msf2blk(make32(make16(0,infobuf[9]),make16(infobuf[10],infobuf[11])));
3218 }
3219 }
3220 for (i=0;i<response_count;i++)
3221 sprintf(&msgbuf[i*3], " %02X", infobuf[i]);
3222 msgbuf[i*3]=0;
3223 msg(DBG_MUL,"MultiSession Info:%s (%d)\n", msgbuf, D_S[d].lba_multi);
3224 if (D_S[d].lba_multi>200)
3225 {
3226 D_S[d].f_multisession=1;
3227 msg(DBG_MUL,"MultiSession base: %06X\n", D_S[d].lba_multi);
3228 }
3229 return (0);
3230}
3231
3232#if FUTURE
3233static int cc_SubChanInfo(int frame, int count, u_char *buffer)
3234
3235{
3236 int i;
3237
3238 if (fam0LV_drive) return (-ENOSYS);
3239 if (famT_drive)
3240 {
3241 return (-1);
3242 }
3243#if 0
3244 if (D_S[d].audio_state!=audio_playing) return (-ENODATA);
3245#endif
3246 clr_cmdbuf();
3247 drvcmd[0]=CMD1_SUBCHANINF;
3248 drvcmd[1]=(frame>>16)&0xFF;
3249 drvcmd[2]=(frame>>8)&0xFF;
3250 drvcmd[3]=frame&0xFF;
3251 drvcmd[5]=(count>>8)&0xFF;
3252 drvcmd[6]=count&0xFF;
3253 flags_cmd_out=f_putcmd|f_respo2|f_ResponseStatus|f_obey_p_check;
3254 cmd_type=READ_SC;
3255 D_S[d].frame_size=CD_FRAMESIZE_SUB;
3256 i=cmd_out();
3257 return (i);
3258}
3259#endif
3260
3261static void __init check_datarate(void)
3262{
3263 int i=0;
3264
3265 msg(DBG_IOX,"check_datarate entered.\n");
3266 datarate=0;
3267#if TEST_STI
3268 for (i=0;i<=1000;i++) printk(".");
3269#endif
3270
3271#if 1
3272 del_timer(&delay_timer);
3273#endif
3274 delay_timer.expires=jiffies+11*HZ/10;
3275 timed_out_delay=0;
3276 add_timer(&delay_timer);
3277#if 0
3278 msg(DBG_TIM,"delay timer started (11*HZ/10).\n");
3279#endif
3280 do
3281 {
3282 i=inb(CDi_status);
3283 datarate++;
3284#if 1
3285 if (datarate>0x6FFFFFFF) break;
3286#endif
3287 }
3288 while (!timed_out_delay);
3289 del_timer(&delay_timer);
3290#if 0
3291 msg(DBG_TIM,"datarate: %04X\n", datarate);
3292#endif
3293 if (datarate<65536) datarate=65536;
3294 maxtim16=datarate*16;
3295 maxtim04=datarate*4;
3296 maxtim02=datarate*2;
3297 maxtim_8=datarate/32;
3298#if LONG_TIMING
3299 maxtim_data=datarate/100;
3300#else
3301 maxtim_data=datarate/300;
3302#endif
3303#if 0
3304 msg(DBG_TIM,"maxtim_8 %d, maxtim_data %d.\n", maxtim_8, maxtim_data);
3305#endif
3306}
3307
3308#if 0
3309static int c2_ReadError(int fam)
3310{
3311 int i;
3312
3313 clr_cmdbuf();
3314 response_count=9;
3315 clr_respo_buf(9);
3316 if (fam==1)
3317 {
3318 drvcmd[0]=CMD0_READ_ERR;
3319 i=do_cmd(f_putcmd|f_lopsta|f_getsta|f_ResponseStatus);
3320 }
3321 else if (fam==2)
3322 {
3323 drvcmd[0]=CMD2_READ_ERR;
3324 i=do_cmd(f_putcmd);
3325 }
3326 else return (-1);
3327 return (i);
3328}
3329#endif
3330
3331static void __init ask_mail(void)
3332{
3333 int i;
3334
3335 msg(DBG_INF, "please mail the following lines to emoenke@gwdg.de\n");
3336 msg(DBG_INF, "(don't mail if you are not using the actual kernel):\n");
3337 msg(DBG_INF, "%s\n", VERSION);
3338 msg(DBG_INF, "address %03X, type %s, drive %s (ID %d)\n",
3339 CDo_command, type, D_S[d].drive_model, D_S[d].drv_id);
3340 for (i=0;i<12;i++)
3341 sprintf(&msgbuf[i*3], " %02X", infobuf[i]);
3342 msgbuf[i*3]=0;
3343 msg(DBG_INF,"infobuf =%s\n", msgbuf);
3344 for (i=0;i<12;i++)
3345 sprintf(&msgbuf[i*3], " %c ", infobuf[i]);
3346 msgbuf[i*3]=0;
3347 msg(DBG_INF,"infobuf =%s\n", msgbuf);
3348}
3349
3350static int __init check_version(void)
3351{
3352 int i, j, l;
3353 int teac_possible=0;
3354
3355 msg(DBG_INI,"check_version: id=%d, d=%d.\n", D_S[d].drv_id, d);
3356 D_S[d].drv_type=0;
3357
3358
3359
3360 clr_cmdbuf();
3361 drvcmd[0]=CMD0_READ_ERR;
3362 response_count=9;
3363 flags_cmd_out=f_putcmd;
3364 i=cmd_out();
3365 if (i<0) msg(DBG_INI,"CMD0_READ_ERR returns %d (ok anyway).\n",i);
3366
3367 clr_cmdbuf();
3368 for (i=0;i<12;i++) infobuf[i]=0;
3369 drvcmd[0]=CMD0_READ_VER;
3370 response_count=12;
3371 flags_cmd_out=f_putcmd;
3372 i=cmd_out();
3373 if (i<-1) msg(DBG_INI,"CMD0_READ_VER returns %d\n",i);
3374 if (i==-11) teac_possible++;
3375 j=0;
3376 for (i=0;i<12;i++) j+=infobuf[i];
3377 if (j)
3378 {
3379 for (i=0;i<12;i++)
3380 sprintf(&msgbuf[i*3], " %02X", infobuf[i]);
3381 msgbuf[i*3]=0;
3382 msg(DBG_ECS,"infobuf =%s\n", msgbuf);
3383 for (i=0;i<12;i++)
3384 sprintf(&msgbuf[i*3], " %c ", infobuf[i]);
3385 msgbuf[i*3]=0;
3386 msg(DBG_ECS,"infobuf =%s\n", msgbuf);
3387 }
3388 for (i=0;i<4;i++) if (infobuf[i]!=family1[i]) break;
3389 if (i==4)
3390 {
3391 D_S[d].drive_model[0]='C';
3392 D_S[d].drive_model[1]='R';
3393 D_S[d].drive_model[2]='-';
3394 D_S[d].drive_model[3]='5';
3395 D_S[d].drive_model[4]=infobuf[i++];
3396 D_S[d].drive_model[5]=infobuf[i++];
3397 D_S[d].drive_model[6]=0;
3398 D_S[d].drv_type=drv_fam1;
3399 }
3400 if (!D_S[d].drv_type)
3401 {
3402 for (i=0;i<8;i++) if (infobuf[i]!=family0[i]) break;
3403 if (i==8)
3404 {
3405 D_S[d].drive_model[0]='C';
3406 D_S[d].drive_model[1]='R';
3407 D_S[d].drive_model[2]='-';
3408 D_S[d].drive_model[3]='5';
3409 D_S[d].drive_model[4]='2';
3410 D_S[d].drive_model[5]='x';
3411 D_S[d].drive_model[6]=0;
3412 D_S[d].drv_type=drv_fam0;
3413 }
3414 }
3415 if (!D_S[d].drv_type)
3416 {
3417 for (i=0;i<8;i++) if (infobuf[i]!=familyL[i]) break;
3418 if (i==8)
3419 {
3420 for (j=0;j<8;j++)
3421 D_S[d].drive_model[j]=infobuf[j];
3422 D_S[d].drive_model[8]=0;
3423 D_S[d].drv_type=drv_famL;
3424 }
3425 }
3426 if (!D_S[d].drv_type)
3427 {
3428 for (i=0;i<6;i++) if (infobuf[i]!=familyV[i]) break;
3429 if (i==6)
3430 {
3431 for (j=0;j<6;j++)
3432 D_S[d].drive_model[j]=infobuf[j];
3433 D_S[d].drive_model[6]=0;
3434 D_S[d].drv_type=drv_famV;
3435 i+=2;
3436 }
3437 }
3438 if (!D_S[d].drv_type)
3439 {
3440
3441 clr_cmdbuf();
3442 drvcmd[0]=CMD2_READ_ERR;
3443 response_count=9;
3444 flags_cmd_out=f_putcmd;
3445 i=cmd_out();
3446 if (i<0) msg(DBG_INI,"CMD2_READERR returns %d (ok anyway).\n",i);
3447 if (i<0) msg(DBG_000,"CMD2_READERR returns %d (ok anyway).\n",i);
3448
3449 clr_cmdbuf();
3450 for (i=0;i<12;i++) infobuf[i]=0;
3451 if (sbpro_type==1) OUT(CDo_sel_i_d,0);
3452#if 0
3453 OUT(CDo_reset,0);
3454 sbp_sleep(6*HZ);
3455 OUT(CDo_enable,D_S[d].drv_sel);
3456#endif
3457 drvcmd[0]=CMD2_READ_VER;
3458 response_count=12;
3459 flags_cmd_out=f_putcmd;
3460 i=cmd_out();
3461 if (i<0) msg(DBG_INI,"CMD2_READ_VER returns %d\n",i);
3462 if (i==-7) teac_possible++;
3463 j=0;
3464 for (i=0;i<12;i++) j+=infobuf[i];
3465 if (j)
3466 {
3467 for (i=0;i<12;i++)
3468 sprintf(&msgbuf[i*3], " %02X", infobuf[i]);
3469 msgbuf[i*3]=0;
3470 msg(DBG_IDX,"infobuf =%s\n", msgbuf);
3471 for (i=0;i<12;i++)
3472 sprintf(&msgbuf[i*3], " %c ", infobuf[i]);
3473 msgbuf[i*3]=0;
3474 msg(DBG_IDX,"infobuf =%s\n", msgbuf);
3475 }
3476 if (i>=0)
3477 {
3478 for (i=0;i<5;i++) if (infobuf[i]!=family2[i]) break;
3479 if (i==5)
3480 {
3481 D_S[d].drive_model[0]='C';
3482 D_S[d].drive_model[1]='D';
3483 D_S[d].drive_model[2]='2';
3484 D_S[d].drive_model[3]='0';
3485 D_S[d].drive_model[4]='0';
3486 D_S[d].drive_model[5]=infobuf[i++];
3487 D_S[d].drive_model[6]=infobuf[i++];
3488 D_S[d].drive_model[7]=0;
3489 D_S[d].drv_type=drv_fam2;
3490 }
3491 }
3492 }
3493 if (!D_S[d].drv_type)
3494 {
3495
3496 msg(DBG_TEA,"teac_possible: %d\n",teac_possible);
3497 for (j=1;j<=((D_S[d].drv_id==0)?3:1);j++)
3498 {
3499 for (l=1;l<=((D_S[d].drv_id==0)?10:1);l++)
3500 {
3501 msg(DBG_TEA,"TEAC reset #%d-%d.\n", j, l);
3502 if (sbpro_type==1) OUT(CDo_reset,0);
3503 else
3504 {
3505 OUT(CDo_enable,D_S[d].drv_sel);
3506 OUT(CDo_sel_i_d,0);
3507 OUT(CDo_command,CMDT_RESET);
3508 for (i=0;i<9;i++) OUT(CDo_command,0);
3509 }
3510 sbp_sleep(5*HZ/10);
3511 OUT(CDo_enable,D_S[d].drv_sel);
3512 OUT(CDo_sel_i_d,0);
3513 i=inb(CDi_status);
3514 msg(DBG_TEA,"TEAC CDi_status: %02X.\n",i);
3515#if 0
3516 if (i&s_not_result_ready) continue;
3517#endif
3518 i=inb(CDi_info);
3519 msg(DBG_TEA,"TEAC CDi_info: %02X.\n",i);
3520 if (i==0x55) break;
3521 }
3522 if (i==0x55) break;
3523 }
3524 if (i==0x55)
3525 {
3526 msg(DBG_TEA,"TEAC drive found.\n");
3527 clr_cmdbuf();
3528 flags_cmd_out=f_putcmd;
3529 response_count=12;
3530 drvcmd[0]=CMDT_READ_VER;
3531 drvcmd[4]=response_count;
3532 for (i=0;i<12;i++) infobuf[i]=0;
3533 i=cmd_out_T();
3534 if (i!=0) msg(DBG_TEA,"cmd_out_T(CMDT_READ_VER) returns %d.\n",i);
3535 for (i=1;i<6;i++) if (infobuf[i]!=familyT[i-1]) break;
3536 if (i==6)
3537 {
3538 D_S[d].drive_model[0]='C';
3539 D_S[d].drive_model[1]='D';
3540 D_S[d].drive_model[2]='-';
3541 D_S[d].drive_model[3]='5';
3542 D_S[d].drive_model[4]='5';
3543 D_S[d].drive_model[5]=0;
3544 D_S[d].drv_type=drv_famT;
3545 }
3546 }
3547 }
3548 if (!D_S[d].drv_type)
3549 {
3550 msg(DBG_TEA,"no drive found at address %03X under ID %d.\n",CDo_command,D_S[d].drv_id);
3551 return (-522);
3552 }
3553 for (j=0;j<4;j++) D_S[d].firmware_version[j]=infobuf[i+j];
3554 if (famL_drive)
3555 {
3556 u_char lcs_firm_e1[]="A E1";
3557 u_char lcs_firm_f4[]="A4F4";
3558
3559 for (j=0;j<4;j++)
3560 if (D_S[d].firmware_version[j]!=lcs_firm_e1[j]) break;
3561 if (j==4) D_S[d].drv_type=drv_e1;
3562
3563 for (j=0;j<4;j++)
3564 if (D_S[d].firmware_version[j]!=lcs_firm_f4[j]) break;
3565 if (j==4) D_S[d].drv_type=drv_f4;
3566
3567 if (D_S[d].drv_type==drv_famL) ask_mail();
3568 }
3569 else if (famT_drive)
3570 {
3571 j=infobuf[4];
3572 if (j=='5')
3573 {
3574 D_S[d].firmware_version[0]=infobuf[7];
3575 D_S[d].firmware_version[1]=infobuf[8];
3576 D_S[d].firmware_version[2]=infobuf[10];
3577 D_S[d].firmware_version[3]=infobuf[11];
3578 }
3579 else
3580 {
3581 if (j!=0x15) ask_mail();
3582 D_S[d].firmware_version[0]='0';
3583 D_S[d].firmware_version[1]='.';
3584 D_S[d].firmware_version[2]='0'+(j>>4);
3585 D_S[d].firmware_version[3]='0'+(j&0x0f);
3586 }
3587 }
3588 else
3589 {
3590 j = (D_S[d].firmware_version[0] & 0x0F) * 100 +
3591 (D_S[d].firmware_version[2] & 0x0F) *10 +
3592 (D_S[d].firmware_version[3] & 0x0F);
3593 if (fam0_drive)
3594 {
3595 if (j<200) D_S[d].drv_type=drv_199;
3596 else if (j<201) D_S[d].drv_type=drv_200;
3597 else if (j<210) D_S[d].drv_type=drv_201;
3598 else if (j<211) D_S[d].drv_type=drv_210;
3599 else if (j<300) D_S[d].drv_type=drv_211;
3600 else if (j>=300) D_S[d].drv_type=drv_300;
3601 }
3602 else if (fam1_drive)
3603 {
3604 if (j<100) D_S[d].drv_type=drv_099;
3605 else
3606 {
3607 D_S[d].drv_type=drv_100;
3608 if ((j!=500)&&(j!=102)) ask_mail();
3609 }
3610 }
3611 else if (fam2_drive)
3612 {
3613 if (D_S[d].drive_model[5]=='F')
3614 {
3615 if ((j!=1)&&(j!=35)&&(j!=200)&&(j!=210))
3616 ask_mail();
3617 }
3618 else
3619 {
3620 msg(DBG_INF,"this CD200 drive is not fully supported yet - only audio will work.\n");
3621 if ((j!=101)&&(j!=35))
3622 ask_mail();
3623 }
3624 }
3625 else if (famV_drive)
3626 {
3627 if ((j==100)||(j==150)) D_S[d].drv_type=drv_at;
3628 ask_mail();
3629 }
3630 }
3631 msg(DBG_LCS,"drive type %02X\n",D_S[d].drv_type);
3632 msg(DBG_INI,"check_version done.\n");
3633 return (0);
3634}
3635
3636static void switch_drive(int i)
3637{
3638 d=i;
3639 OUT(CDo_enable,D_S[d].drv_sel);
3640 msg(DBG_DID,"drive %d (ID=%d) activated.\n", i, D_S[d].drv_id);
3641 return;
3642}
3643
3644#ifdef PATH_CHECK
3645
3646
3647
3648static int __init check_card(int port)
3649{
3650#undef N_RESPO
3651#define N_RESPO 20
3652 int i, j, k;
3653 u_char response[N_RESPO];
3654 u_char save_port0;
3655 u_char save_port3;
3656
3657 msg(DBG_INI,"check_card entered.\n");
3658 save_port0=inb(port+0);
3659 save_port3=inb(port+3);
3660
3661 for (j=0;j<NR_SBPCD;j++)
3662 {
3663 OUT(port+3,j) ;
3664 OUT(port+0,CMD0_PATH_CHECK);
3665 for (i=10;i>0;i--) OUT(port+0,0);
3666 for (k=0;k<N_RESPO;k++) response[k]=0;
3667 for (k=0;k<N_RESPO;k++)
3668 {
3669 for (i=10000;i>0;i--)
3670 {
3671 if (inb(port+1)&s_not_result_ready) continue;
3672 response[k]=inb(port+0);
3673 break;
3674 }
3675 }
3676 for (i=0;i<N_RESPO;i++)
3677 sprintf(&msgbuf[i*3], " %02X", response[i]);
3678 msgbuf[i*3]=0;
3679 msg(DBG_TEA,"path check 00 (%d): %s\n", j, msgbuf);
3680 OUT(port+0,CMD0_PATH_CHECK);
3681 for (i=10;i>0;i--) OUT(port+0,0);
3682 for (k=0;k<N_RESPO;k++) response[k]=0xFF;
3683 for (k=0;k<N_RESPO;k++)
3684 {
3685 for (i=10000;i>0;i--)
3686 {
3687 if (inb(port+1)&s_not_result_ready) continue;
3688 response[k]=inb(port+0);
3689 break;
3690 }
3691 }
3692 for (i=0;i<N_RESPO;i++)
3693 sprintf(&msgbuf[i*3], " %02X", response[i]);
3694 msgbuf[i*3]=0;
3695 msg(DBG_TEA,"path check 00 (%d): %s\n", j, msgbuf);
3696
3697 if (response[0]==0xAA)
3698 if (response[1]==0x55)
3699 return (0);
3700 }
3701 for (j=0;j<NR_SBPCD;j++)
3702 {
3703 OUT(port+3,j) ;
3704 OUT(port+0,CMD2_READ_VER);
3705 for (i=10;i>0;i--) OUT(port+0,0);
3706 for (k=0;k<N_RESPO;k++) response[k]=0;
3707 for (k=0;k<N_RESPO;k++)
3708 {
3709 for (i=1000000;i>0;i--)
3710 {
3711 if (inb(port+1)&s_not_result_ready) continue;
3712 response[k]=inb(port+0);
3713 break;
3714 }
3715 }
3716 for (i=0;i<N_RESPO;i++)
3717 sprintf(&msgbuf[i*3], " %02X", response[i]);
3718 msgbuf[i*3]=0;
3719 msg(DBG_TEA,"path check 12 (%d): %s\n", j, msgbuf);
3720
3721 OUT(port+0,CMD2_READ_VER);
3722 for (i=10;i>0;i--) OUT(port+0,0);
3723 for (k=0;k<N_RESPO;k++) response[k]=0xFF;
3724 for (k=0;k<N_RESPO;k++)
3725 {
3726 for (i=1000000;i>0;i--)
3727 {
3728 if (inb(port+1)&s_not_result_ready) continue;
3729 response[k]=inb(port+0);
3730 break;
3731 }
3732 }
3733 for (i=0;i<N_RESPO;i++)
3734 sprintf(&msgbuf[i*3], " %02X", response[i]);
3735 msgbuf[i*3]=0;
3736 msg(DBG_TEA,"path check 12 (%d): %s\n", j, msgbuf);
3737
3738 if (response[0]==0xAA)
3739 if (response[1]==0x55)
3740 return (0);
3741 }
3742 OUT(port+0,save_port0);
3743 OUT(port+3,save_port3);
3744 return (0);
3745}
3746#endif
3747
3748
3749
3750
3751
3752static int __init check_drives(void)
3753{
3754 int i, j;
3755
3756 msg(DBG_INI,"check_drives entered.\n");
3757 ndrives=0;
3758 for (j=0;j<max_drives;j++)
3759 {
3760 D_S[ndrives].drv_id=j;
3761 if (sbpro_type==1) D_S[ndrives].drv_sel=(j&0x01)<<1|(j&0x02)>>1;
3762 else D_S[ndrives].drv_sel=j;
3763 switch_drive(ndrives);
3764 msg(DBG_INI,"check_drives: drive %d (ID=%d) activated.\n",ndrives,j);
3765 msg(DBG_000,"check_drives: drive %d (ID=%d) activated.\n",ndrives,j);
3766 i=check_version();
3767 if (i<0) msg(DBG_INI,"check_version returns %d.\n",i);
3768 else
3769 {
3770 D_S[d].drv_options=drv_pattern[j];
3771 if (fam0L_drive) D_S[d].drv_options&=~(speed_auto|speed_300|speed_150);
3772 msg(DBG_INF, "Drive %d (ID=%d): %.9s (%.4s) at 0x%03X (type %d)\n",
3773 d,
3774 D_S[d].drv_id,
3775 D_S[d].drive_model,
3776 D_S[d].firmware_version,
3777 CDo_command,
3778 sbpro_type);
3779 ndrives++;
3780 }
3781 }
3782 for (j=ndrives;j<NR_SBPCD;j++) D_S[j].drv_id=-1;
3783 if (ndrives==0) return (-1);
3784 return (0);
3785}
3786
3787#if FUTURE
3788
3789
3790
3791static int obey_audio_state(u_char audio_state, u_char func,u_char subfunc)
3792{
3793 switch (audio_state)
3794 {
3795 case aud_11:
3796 case audx11:
3797 switch (func)
3798 {
3799 case cmd_07:
3800 case cmd_0d:
3801 case cmd_0e:
3802 case cmd_0c:
3803 return (1);
3804 case cmd_03:
3805 switch (subfunc)
3806
3807 {
3808 case cxi_00:
3809 case cxi_06:
3810 case cxi_09:
3811 return (1);
3812 default:
3813 return (ERROR15);
3814 }
3815 return (1);
3816 default:
3817 return (ERROR15);
3818 }
3819 return (1);
3820 case aud_12:
3821 case audx12:
3822 return (1);
3823 default:
3824 return (2);
3825 }
3826}
3827
3828
3829
3830
3831
3832
3833static int check_allowed1(u_char func1, u_char func2)
3834{
3835#if 000
3836 if (func1==ioctl_o) return (0);
3837 if (func1==read_long) return (-1);
3838 if (func1==read_long_prefetch) return (-1);
3839 if (func1==seek) return (-1);
3840 if (func1==audio_play) return (-1);
3841 if (func1==audio_pause) return (-1);
3842 if (func1==audio_resume) return (-1);
3843 if (func1!=ioctl_i) return (0);
3844 if (func2==tell_SubQ_run_tot) return (-1);
3845 if (func2==tell_cdsize) return (-1);
3846 if (func2==tell_TocDescrip) return (-1);
3847 if (func2==tell_TocEntry) return (-1);
3848 if (func2==tell_subQ_info) return (-1);
3849 if (fam1_drive) if (func2==tell_SubChanInfo) return (-1);
3850 if (func2==tell_UPC) return (-1);
3851#else
3852 return (0);
3853#endif
3854}
3855
3856static int check_allowed2(u_char func1, u_char func2)
3857{
3858#if 000
3859 if (func1==read_long) return (-1);
3860 if (func1==read_long_prefetch) return (-1);
3861 if (func1==seek) return (-1);
3862 if (func1==audio_play) return (-1);
3863 if (func1!=ioctl_o) return (0);
3864 if (fam1_drive)
3865 {
3866 if (func2==EjectDisk) return (-1);
3867 if (func2==CloseTray) return (-1);
3868 }
3869#else
3870 return (0);
3871#endif
3872}
3873
3874static int check_allowed3(u_char func1, u_char func2)
3875{
3876#if 000
3877 if (func1==ioctl_i)
3878 {
3879 if (func2==tell_address) return (0);
3880 if (func2==tell_capabiliti) return (0);
3881 if (func2==tell_CD_changed) return (0);
3882 if (fam0L_drive) if (func2==tell_SubChanInfo) return (0);
3883 return (-1);
3884 }
3885 if (func1==ioctl_o)
3886 {
3887 if (func2==DriveReset) return (0);
3888 if (fam0L_drive)
3889 {
3890 if (func2==EjectDisk) return (0);
3891 if (func2==LockDoor) return (0);
3892 if (func2==CloseTray) return (0);
3893 }
3894 return (-1);
3895 }
3896 if (func1==flush_input) return (-1);
3897 if (func1==read_long) return (-1);
3898 if (func1==read_long_prefetch) return (-1);
3899 if (func1==seek) return (-1);
3900 if (func1==audio_play) return (-1);
3901 if (func1==audio_pause) return (-1);
3902 if (func1==audio_resume) return (-1);
3903#else
3904 return (0);
3905#endif
3906}
3907
3908static int seek_pos_audio_end(void)
3909{
3910 int i;
3911
3912 i=msf2blk(D_S[d].pos_audio_end)-1;
3913 if (i<0) return (-1);
3914 i=cc_Seek(i,0);
3915 return (i);
3916}
3917#endif
3918
3919static int ReadToC(void)
3920{
3921 int i, j;
3922 D_S[d].diskstate_flags &= ~toc_bit;
3923 D_S[d].ored_ctl_adr=0;
3924
3925 if ((D_S[d].n_first_track == 2 && D_S[d].n_last_track == 2) ||
3926 D_S[d].xa_byte == 0x10)
3927 {
3928 D_S[d].TocBuffer[1].nixbyte=0;
3929 D_S[d].TocBuffer[1].ctl_adr=0x40;
3930 D_S[d].TocBuffer[1].number=1;
3931 D_S[d].TocBuffer[1].format=0;
3932 D_S[d].TocBuffer[1].address=blk2msf(0);
3933 D_S[d].ored_ctl_adr |= 0x40;
3934 D_S[d].n_first_track = 1;
3935 D_S[d].n_last_track = 1;
3936 D_S[d].xa_byte = 0x10;
3937 j = 2;
3938 } else
3939 for (j=D_S[d].n_first_track;j<=D_S[d].n_last_track;j++)
3940 {
3941 i=cc_ReadTocEntry(j);
3942 if (i<0)
3943 {
3944 msg(DBG_INF,"cc_ReadTocEntry(%d) returns %d.\n",j,i);
3945 return (i);
3946 }
3947 D_S[d].TocBuffer[j].nixbyte=D_S[d].TocEnt_nixbyte;
3948 D_S[d].TocBuffer[j].ctl_adr=D_S[d].TocEnt_ctl_adr;
3949 D_S[d].TocBuffer[j].number=D_S[d].TocEnt_number;
3950 D_S[d].TocBuffer[j].format=D_S[d].TocEnt_format;
3951 D_S[d].TocBuffer[j].address=D_S[d].TocEnt_address;
3952 D_S[d].ored_ctl_adr |= D_S[d].TocEnt_ctl_adr;
3953 }
3954
3955 D_S[d].TocBuffer[j].nixbyte=0;
3956 D_S[d].TocBuffer[j].ctl_adr=0;
3957 D_S[d].TocBuffer[j].number=CDROM_LEADOUT;
3958 D_S[d].TocBuffer[j].format=0;
3959 D_S[d].TocBuffer[j].address=D_S[d].size_msf;
3960
3961 D_S[d].diskstate_flags |= toc_bit;
3962 return (0);
3963}
3964
3965static int DiskInfo(void)
3966{
3967 int i, j;
3968
3969 D_S[d].mode=READ_M1;
3970
3971#undef LOOP_COUNT
3972#define LOOP_COUNT 10
3973
3974 msg(DBG_000,"DiskInfo entered.\n");
3975 for (j=1;j<LOOP_COUNT;j++)
3976 {
3977#if 0
3978 i=SetSpeed();
3979 if (i<0)
3980 {
3981 msg(DBG_INF,"DiskInfo: SetSpeed returns %d\n", i);
3982 continue;
3983 }
3984 i=cc_ModeSense();
3985 if (i<0)
3986 {
3987 msg(DBG_INF,"DiskInfo: cc_ModeSense returns %d\n", i);
3988 continue;
3989 }
3990#endif
3991 i=cc_ReadCapacity();
3992 if (i>=0) break;
3993 msg(DBG_INF,"DiskInfo: ReadCapacity #%d returns %d\n", j, i);
3994#if 0
3995 i=cc_DriveReset();
3996#endif
3997 if (!fam0_drive && j == 2) break;
3998 }
3999 if (j==LOOP_COUNT) return (-33);
4000
4001 i=cc_ReadTocDescr();
4002 if (i<0)
4003 {
4004 msg(DBG_INF,"DiskInfo: ReadTocDescr returns %d\n", i);
4005 return (i);
4006 }
4007 i=ReadToC();
4008 if (i<0)
4009 {
4010 msg(DBG_INF,"DiskInfo: ReadToC returns %d\n", i);
4011 return (i);
4012 }
4013 i=cc_CheckMultiSession();
4014 if (i<0)
4015 {
4016 msg(DBG_INF,"DiskInfo: cc_CheckMultiSession returns %d\n", i);
4017 return (i);
4018 }
4019 if (D_S[d].f_multisession) D_S[d].sbp_bufsiz=1;
4020 else D_S[d].sbp_bufsiz=buffers;
4021 i=cc_ReadTocEntry(D_S[d].n_first_track);
4022 if (i<0)
4023 {
4024 msg(DBG_INF,"DiskInfo: cc_ReadTocEntry(1) returns %d\n", i);
4025 return (i);
4026 }
4027 i=cc_ReadUPC();
4028 if (i<0) msg(DBG_INF,"DiskInfo: cc_ReadUPC returns %d\n", i);
4029 if ((fam0L_drive) && (D_S[d].xa_byte==0x20 || D_S[d].xa_byte == 0x10))
4030 {
4031
4032 cc_ModeSelect(CD_FRAMESIZE_RAW1);
4033 cc_ModeSense();
4034 }
4035 if (famT_drive) cc_prep_mode_T();
4036 msg(DBG_000,"DiskInfo done.\n");
4037 return (0);
4038}
4039
4040static int sbpcd_drive_status(struct cdrom_device_info *cdi, int slot_nr)
4041{
4042 int st;
4043
4044 if (CDSL_CURRENT != slot_nr) {
4045
4046 return -EINVAL;
4047 }
4048
4049 cc_ReadStatus();
4050 st=ResponseStatus();
4051 if (st<0)
4052 {
4053 msg(DBG_INF,"sbpcd_drive_status: timeout.\n");
4054 return (0);
4055 }
4056 msg(DBG_000,"Drive Status: door_locked =%d.\n", st_door_locked);
4057 msg(DBG_000,"Drive Status: door_closed =%d.\n", st_door_closed);
4058 msg(DBG_000,"Drive Status: caddy_in =%d.\n", st_caddy_in);
4059 msg(DBG_000,"Drive Status: disk_ok =%d.\n", st_diskok);
4060 msg(DBG_000,"Drive Status: spinning =%d.\n", st_spinning);
4061 msg(DBG_000,"Drive Status: busy =%d.\n", st_busy);
4062
4063#if 0
4064 if (!(D_S[MINOR(cdi->dev)].status_bits & p_door_closed)) return CDS_TRAY_OPEN;
4065 if (D_S[MINOR(cdi->dev)].status_bits & p_disk_ok) return CDS_DISC_OK;
4066 if (D_S[MINOR(cdi->dev)].status_bits & p_disk_in) return CDS_DRIVE_NOT_READY;
4067
4068 return CDS_NO_DISC;
4069#else
4070 if (D_S[MINOR(cdi->dev)].status_bits & p_spinning) return CDS_DISC_OK;
4071
4072 return CDS_NO_DISC;
4073
4074#endif
4075
4076}
4077
4078
4079
4080#if FUTURE
4081
4082
4083
4084
4085static int prepare(u_char func, u_char subfunc)
4086{
4087 int i;
4088
4089 if (fam0L_drive)
4090 {
4091 i=inb(CDi_status);
4092 if (i&s_attention) GetStatus();
4093 }
4094 else if (fam1_drive) GetStatus();
4095 else if (fam2_drive) GetStatus();
4096 else if (famT_drive) GetStatus();
4097 if (D_S[d].CD_changed==0xFF)
4098 {
4099 D_S[d].diskstate_flags=0;
4100 D_S[d].audio_state=0;
4101 if (!st_diskok)
4102 {
4103 i=check_allowed1(func,subfunc);
4104 if (i<0) return (-2);
4105 }
4106 else
4107 {
4108 i=check_allowed3(func,subfunc);
4109 if (i<0)
4110 {
4111 D_S[d].CD_changed=1;
4112 return (-15);
4113 }
4114 }
4115 }
4116 else
4117 {
4118 if (!st_diskok)
4119 {
4120 D_S[d].diskstate_flags=0;
4121 D_S[d].audio_state=0;
4122 i=check_allowed1(func,subfunc);
4123 if (i<0) return (-2);
4124 }
4125 else
4126 {
4127 if (st_busy)
4128 {
4129 if (D_S[d].audio_state!=audio_pausing)
4130 {
4131 i=check_allowed2(func,subfunc);
4132 if (i<0) return (-2);
4133 }
4134 }
4135 else
4136 {
4137 if (D_S[d].audio_state==audio_playing) seek_pos_audio_end();
4138 D_S[d].audio_state=0;
4139 }
4140 if (!frame_size_valid)
4141 {
4142 i=DiskInfo();
4143 if (i<0)
4144 {
4145 D_S[d].diskstate_flags=0;
4146 D_S[d].audio_state=0;
4147 i=check_allowed1(func,subfunc);
4148 if (i<0) return (-2);
4149 }
4150 }
4151 }
4152 }
4153 return (0);
4154}
4155#endif
4156
4157
4158
4159
4160
4161static int sbp_status(void)
4162{
4163 int st;
4164
4165 st=ResponseStatus();
4166 if (st<0)
4167 {
4168 msg(DBG_INF,"sbp_status: timeout.\n");
4169 return (0);
4170 }
4171
4172 if (!st_spinning) msg(DBG_SPI,"motor got off - ignoring.\n");
4173
4174 if (st_check)
4175 {
4176 msg(DBG_INF,"st_check detected - retrying.\n");
4177 return (0);
4178 }
4179 if (!st_door_closed)
4180 {
4181 msg(DBG_INF,"door is open - retrying.\n");
4182 return (0);
4183 }
4184 if (!st_caddy_in)
4185 {
4186 msg(DBG_INF,"disk removed - retrying.\n");
4187 return (0);
4188 }
4189 if (!st_diskok)
4190 {
4191 msg(DBG_INF,"!st_diskok detected - retrying.\n");
4192 return (0);
4193 }
4194 if (st_busy)
4195 {
4196 msg(DBG_INF,"st_busy detected - retrying.\n");
4197 return (0);
4198 }
4199 return (1);
4200}
4201
4202
4203static int sbpcd_get_last_session(struct cdrom_device_info *cdi, struct cdrom_multisession *ms_infp)
4204{
4205 ms_infp->addr_format = CDROM_LBA;
4206 ms_infp->addr.lba = D_S[MINOR(cdi->dev)].lba_multi;
4207 if (D_S[MINOR(cdi->dev)].f_multisession)
4208 ms_infp->xa_flag=1;
4209 else
4210 ms_infp->xa_flag=0;
4211
4212 return 0;
4213}
4214
4215
4216
4217
4218
4219
4220static int sbpcd_dev_ioctl(struct cdrom_device_info *cdi, u_int cmd,
4221 u_long arg)
4222{
4223 int i;
4224
4225 msg(DBG_IO2,"ioctl(%d, 0x%08lX, 0x%08lX)\n",
4226 MINOR(cdi->dev), cmd, arg);
4227 i=MINOR(cdi->dev);
4228 if ((i<0) || (i>=NR_SBPCD) || (D_S[i].drv_id==-1))
4229 {
4230 msg(DBG_INF, "ioctl: bad device: %04X\n", cdi->dev);
4231 return (-ENXIO);
4232 }
4233 down(&ioctl_read_sem);
4234 if (d!=i) switch_drive(i);
4235
4236 msg(DBG_IO2,"ioctl: device %d, request %04X\n",i,cmd);
4237 switch (cmd)
4238 {
4239 case DDIOCSDBG:
4240 if (!capable(CAP_SYS_ADMIN)) RETURN_UP(-EPERM);
4241 i=sbpcd_dbg_ioctl(arg,1);
4242 RETURN_UP(i);
4243 case CDROMRESET:
4244 msg(DBG_IOC,"ioctl: CDROMRESET entered.\n");
4245 i=DriveReset();
4246 D_S[d].audio_state=0;
4247 RETURN_UP(i);
4248
4249 case CDROMREADMODE1:
4250 msg(DBG_IOC,"ioctl: CDROMREADMODE1 requested.\n");
4251#if SAFE_MIXED
4252 if (D_S[d].has_data>1) RETURN_UP(-EBUSY);
4253#endif
4254 cc_ModeSelect(CD_FRAMESIZE);
4255 cc_ModeSense();
4256 D_S[d].mode=READ_M1;
4257 RETURN_UP(0);
4258
4259 case CDROMREADMODE2:
4260 msg(DBG_IOC,"ioctl: CDROMREADMODE2 requested.\n");
4261#if SAFE_MIXED
4262 if (D_S[d].has_data>1) RETURN_UP(-EBUSY);
4263#endif
4264 cc_ModeSelect(CD_FRAMESIZE_RAW1);
4265 cc_ModeSense();
4266 D_S[d].mode=READ_M2;
4267 RETURN_UP(0);
4268
4269 case CDROMAUDIOBUFSIZ:
4270 msg(DBG_IOC,"ioctl: CDROMAUDIOBUFSIZ entered.\n");
4271 if (D_S[d].sbp_audsiz>0) vfree(D_S[d].aud_buf);
4272 D_S[d].aud_buf=NULL;
4273 D_S[d].sbp_audsiz=arg;
4274
4275 if (D_S[d].sbp_audsiz>16)
4276 {
4277 D_S[d].sbp_audsiz = 0;
4278 RETURN_UP(D_S[d].sbp_audsiz);
4279 }
4280
4281 if (D_S[d].sbp_audsiz>0)
4282 {
4283 D_S[d].aud_buf=(u_char *) vmalloc(D_S[d].sbp_audsiz*CD_FRAMESIZE_RAW);
4284 if (D_S[d].aud_buf==NULL)
4285 {
4286 msg(DBG_INF,"audio buffer (%d frames) not available.\n",D_S[d].sbp_audsiz);
4287 D_S[d].sbp_audsiz=0;
4288 }
4289 else msg(DBG_INF,"audio buffer size: %d frames.\n",D_S[d].sbp_audsiz);
4290 }
4291 RETURN_UP(D_S[d].sbp_audsiz);
4292
4293 case CDROMREADAUDIO:
4294 {
4295 int i=0, j=0, frame, block=0;
4296 u_int try=0;
4297 u_long timeout;
4298 u_char *p;
4299 u_int data_tries = 0;
4300 u_int data_waits = 0;
4301 u_int data_retrying = 0;
4302 int status_tries;
4303 int error_flag;
4304
4305 msg(DBG_IOC,"ioctl: CDROMREADAUDIO entered.\n");
4306 if (fam0_drive) RETURN_UP(-EINVAL);
4307 if (famL_drive) RETURN_UP(-EINVAL);
4308 if (famV_drive) RETURN_UP(-EINVAL);
4309 if (famT_drive) RETURN_UP(-EINVAL);
4310#if SAFE_MIXED
4311 if (D_S[d].has_data>1) RETURN_UP(-EBUSY);
4312#endif
4313 if (D_S[d].aud_buf==NULL) RETURN_UP(-EINVAL);
4314 i=verify_area(VERIFY_READ, (void *) arg, sizeof(struct cdrom_read_audio));
4315 if (i) RETURN_UP(i);
4316 copy_from_user(&read_audio, (void *) arg, sizeof(struct cdrom_read_audio));
4317 if (read_audio.nframes < 0 || read_audio.nframes>D_S[d].sbp_audsiz) RETURN_UP(-EINVAL);
4318 i=verify_area(VERIFY_WRITE, read_audio.buf,
4319 read_audio.nframes*CD_FRAMESIZE_RAW);
4320 if (i) RETURN_UP(i);
4321
4322 if (read_audio.addr_format==CDROM_MSF)
4323 block=msf2lba(&read_audio.addr.msf.minute);
4324 else if (read_audio.addr_format==CDROM_LBA)
4325 block=read_audio.addr.lba;
4326 else RETURN_UP(-EINVAL);
4327#if 000
4328 i=cc_SetSpeed(speed_150,0,0);
4329 if (i) msg(DBG_AUD,"read_audio: SetSpeed error %d\n", i);
4330#endif
4331 msg(DBG_AUD,"read_audio: lba: %d, msf: %06X\n",
4332 block, blk2msf(block));
4333 msg(DBG_AUD,"read_audio: before cc_ReadStatus.\n");
4334#if OLD_BUSY
4335 while (busy_data) sbp_sleep(HZ/10);
4336 busy_audio=1;
4337#endif
4338 error_flag=0;
4339 for (data_tries=5; data_tries>0; data_tries--)
4340 {
4341 msg(DBG_AUD,"data_tries=%d ...\n", data_tries);
4342 D_S[d].mode=READ_AU;
4343 cc_ModeSelect(CD_FRAMESIZE_RAW);
4344 cc_ModeSense();
4345 for (status_tries=3; status_tries > 0; status_tries--)
4346 {
4347 flags_cmd_out |= f_respo3;
4348 cc_ReadStatus();
4349 if (sbp_status() != 0) break;
4350 if (st_check) cc_ReadError();
4351 sbp_sleep(1);
4352 }
4353 if (status_tries == 0)
4354 {
4355 msg(DBG_AUD,"read_audio: sbp_status: failed after 3 tries in line %d.\n", __LINE__);
4356 continue;
4357 }
4358 msg(DBG_AUD,"read_audio: sbp_status: ok.\n");
4359
4360 flags_cmd_out = f_putcmd | f_respo2 | f_ResponseStatus | f_obey_p_check;
4361 if (fam0L_drive)
4362 {
4363 flags_cmd_out |= f_lopsta | f_getsta | f_bit1;
4364 cmd_type=READ_M2;
4365 drvcmd[0]=CMD0_READ_XA;
4366 drvcmd[1]=(block>>16)&0x000000ff;
4367 drvcmd[2]=(block>>8)&0x000000ff;
4368 drvcmd[3]=block&0x000000ff;
4369 drvcmd[4]=0;
4370 drvcmd[5]=read_audio.nframes;
4371 drvcmd[6]=0;
4372 }
4373 else if (fam1_drive)
4374 {
4375 drvcmd[0]=CMD1_READ;
4376 lba2msf(block,&drvcmd[1]);
4377 drvcmd[4]=0;
4378 drvcmd[5]=0;
4379 drvcmd[6]=read_audio.nframes;
4380 }
4381 else if (fam2_drive)
4382 {
4383 drvcmd[0]=CMD2_READ_XA2;
4384 lba2msf(block,&drvcmd[1]);
4385 drvcmd[4]=0;
4386 drvcmd[5]=read_audio.nframes;
4387 drvcmd[6]=0x11;
4388 }
4389 else if (famT_drive)
4390 {
4391 }
4392 msg(DBG_AUD,"read_audio: before giving \"read\" command.\n");
4393 flags_cmd_out=f_putcmd;
4394 response_count=0;
4395 i=cmd_out();
4396 if (i<0) msg(DBG_INF,"error giving READ AUDIO command: %0d\n", i);
4397 sbp_sleep(0);
4398 msg(DBG_AUD,"read_audio: after giving \"read\" command.\n");
4399 for (frame=1;frame<2 && !error_flag; frame++)
4400 {
4401 try=maxtim_data;
4402 for (timeout=jiffies+9*HZ; ; )
4403 {
4404 for ( ; try!=0;try--)
4405 {
4406 j=inb(CDi_status);
4407 if (!(j&s_not_data_ready)) break;
4408 if (!(j&s_not_result_ready)) break;
4409 if (fam0L_drive) if (j&s_attention) break;
4410 }
4411 if (try != 0 || time_after_eq(jiffies, timeout)) break;
4412 if (data_retrying == 0) data_waits++;
4413 data_retrying = 1;
4414 sbp_sleep(1);
4415 try = 1;
4416 }
4417 if (try==0)
4418 {
4419 msg(DBG_INF,"read_audio: sbp_data: CDi_status timeout.\n");
4420 error_flag++;
4421 break;
4422 }
4423 msg(DBG_AUD,"read_audio: sbp_data: CDi_status ok.\n");
4424 if (j&s_not_data_ready)
4425 {
4426 msg(DBG_INF, "read_audio: sbp_data: DATA_READY timeout.\n");
4427 error_flag++;
4428 break;
4429 }
4430 msg(DBG_AUD,"read_audio: before reading data.\n");
4431 error_flag=0;
4432 p = D_S[d].aud_buf;
4433 if (sbpro_type==1) OUT(CDo_sel_i_d,1);
4434 if (do_16bit)
4435 {
4436 u_short *p2 = (u_short *) p;
4437
4438 for (; (u_char *) p2 < D_S[d].aud_buf + read_audio.nframes*CD_FRAMESIZE_RAW;)
4439 {
4440 if ((inb_p(CDi_status)&s_not_data_ready)) continue;
4441
4442
4443 *p2++ = inw_p(CDi_data);
4444 *p2++ = inw_p(CDi_data);
4445 }
4446 } else {
4447 for (; p < D_S[d].aud_buf + read_audio.nframes*CD_FRAMESIZE_RAW;)
4448 {
4449 if ((inb_p(CDi_status)&s_not_data_ready)) continue;
4450
4451
4452 *p++ = inb_p(CDi_data);
4453 *p++ = inb_p(CDi_data);
4454 *p++ = inb_p(CDi_data);
4455 *p++ = inb_p(CDi_data);
4456 }
4457 }
4458 if (sbpro_type==1) OUT(CDo_sel_i_d,0);
4459 data_retrying = 0;
4460 }
4461 msg(DBG_AUD,"read_audio: after reading data.\n");
4462 if (error_flag)
4463 {
4464 msg(DBG_AUD,"read_audio: read aborted by drive\n");
4465#if 0000
4466 i=cc_DriveReset();
4467#else
4468 i=cc_ReadError();
4469#endif
4470 continue;
4471 }
4472 if (fam0L_drive)
4473 {
4474 i=maxtim_data;
4475 for (timeout=jiffies+9*HZ; time_before(jiffies, timeout); timeout--)
4476 {
4477 for ( ;i!=0;i--)
4478 {
4479 j=inb(CDi_status);
4480 if (!(j&s_not_data_ready)) break;
4481 if (!(j&s_not_result_ready)) break;
4482 if (j&s_attention) break;
4483 }
4484 if (i != 0 || time_after_eq(jiffies, timeout)) break;
4485 sbp_sleep(0);
4486 i = 1;
4487 }
4488 if (i==0) msg(DBG_AUD,"read_audio: STATUS TIMEOUT AFTER READ");
4489 if (!(j&s_attention))
4490 {
4491 msg(DBG_AUD,"read_audio: sbp_data: timeout waiting DRV_ATTN - retrying\n");
4492 i=cc_DriveReset();
4493 continue;
4494 }
4495 }
4496 do
4497 {
4498 if (fam0L_drive) cc_ReadStatus();
4499 i=ResponseStatus();
4500 if (i<0) { msg(DBG_AUD,
4501 "read_audio: cc_ReadStatus error after read: %02X\n",
4502 D_S[d].status_bits);
4503 continue;
4504 }
4505 }
4506 while ((fam0L_drive)&&(!st_check)&&(!(i&p_success)));
4507 if (st_check)
4508 {
4509 i=cc_ReadError();
4510 msg(DBG_AUD,"read_audio: cc_ReadError was necessary after read: %02X\n",i);
4511 continue;
4512 }
4513 copy_to_user((u_char *) read_audio.buf,
4514 (u_char *) D_S[d].aud_buf,
4515 read_audio.nframes*CD_FRAMESIZE_RAW);
4516 msg(DBG_AUD,"read_audio: copy_to_user done.\n");
4517 break;
4518 }
4519 cc_ModeSelect(CD_FRAMESIZE);
4520 cc_ModeSense();
4521 D_S[d].mode=READ_M1;
4522#if OLD_BUSY
4523 busy_audio=0;
4524#endif
4525 if (data_tries == 0)
4526 {
4527 msg(DBG_AUD,"read_audio: failed after 5 tries in line %d.\n", __LINE__);
4528 RETURN_UP(-EIO);
4529 }
4530 msg(DBG_AUD,"read_audio: successful return.\n");
4531 RETURN_UP(0);
4532 }
4533
4534 case BLKRASET:
4535 if(!capable(CAP_SYS_ADMIN)) RETURN_UP(-EACCES);
4536 if(!(cdi->dev)) RETURN_UP(-EINVAL);
4537 if(arg > 0xff) RETURN_UP(-EINVAL);
4538 read_ahead[MAJOR(cdi->dev)] = arg;
4539 RETURN_UP(0);
4540 default:
4541 msg(DBG_IOC,"ioctl: unknown function request %04X\n", cmd);
4542 RETURN_UP(-EINVAL);
4543 }
4544}
4545
4546static int sbpcd_audio_ioctl(struct cdrom_device_info *cdi, u_int cmd,
4547 void * arg)
4548{
4549 int i, st, j;
4550
4551 msg(DBG_IO2,"ioctl(%d, 0x%08lX, 0x%08p)\n",
4552 MINOR(cdi->dev), cmd, arg);
4553 i=MINOR(cdi->dev);
4554 if ((i<0) || (i>=NR_SBPCD) || (D_S[i].drv_id==-1))
4555 {
4556 msg(DBG_INF, "ioctl: bad device: %04X\n", cdi->dev);
4557 return (-ENXIO);
4558 }
4559 down(&ioctl_read_sem);
4560 if (d!=i) switch_drive(i);
4561
4562 msg(DBG_IO2,"ioctl: device %d, request %04X\n",i,cmd);
4563 switch (cmd)
4564 {
4565
4566 case CDROMPAUSE:
4567 msg(DBG_IOC,"ioctl: CDROMPAUSE entered.\n");
4568
4569
4570
4571
4572 switch (D_S[d].audio_state)
4573 {
4574 case audio_playing:
4575 if (famL_drive) i=cc_ReadSubQ();
4576 else i=cc_Pause_Resume(1);
4577 if (i<0) RETURN_UP(-EIO);
4578 if (famL_drive) i=cc_Pause_Resume(1);
4579 else i=cc_ReadSubQ();
4580 if (i<0) RETURN_UP(-EIO);
4581 D_S[d].pos_audio_start=D_S[d].SubQ_run_tot;
4582 D_S[d].audio_state=audio_pausing;
4583 RETURN_UP(0);
4584 case audio_pausing:
4585 i=cc_Seek(D_S[d].pos_audio_start,1);
4586 if (i<0) RETURN_UP(-EIO);
4587 RETURN_UP(0);
4588 default:
4589 RETURN_UP(-EINVAL);
4590 }
4591
4592 case CDROMRESUME:
4593 msg(DBG_IOC,"ioctl: CDROMRESUME entered.\n");
4594
4595
4596
4597 if (D_S[d].audio_state!=audio_pausing) RETURN_UP(-EINVAL);
4598 if (famL_drive)
4599 i=cc_PlayAudio(D_S[d].pos_audio_start,
4600 D_S[d].pos_audio_end);
4601 else i=cc_Pause_Resume(3);
4602 if (i<0) RETURN_UP(-EIO);
4603 D_S[d].audio_state=audio_playing;
4604 RETURN_UP(0);
4605
4606 case CDROMPLAYMSF:
4607 msg(DBG_IOC,"ioctl: CDROMPLAYMSF entered.\n");
4608#if SAFE_MIXED
4609 if (D_S[d].has_data>1) RETURN_UP(-EBUSY);
4610#endif
4611 if (D_S[d].audio_state==audio_playing)
4612 {
4613 i=cc_Pause_Resume(1);
4614 if (i<0) RETURN_UP(-EIO);
4615 i=cc_ReadSubQ();
4616 if (i<0) RETURN_UP(-EIO);
4617 D_S[d].pos_audio_start=D_S[d].SubQ_run_tot;
4618 i=cc_Seek(D_S[d].pos_audio_start,1);
4619 }
4620 memcpy(&msf, (void *) arg, sizeof(struct cdrom_msf));
4621
4622 D_S[d].pos_audio_start = (msf.cdmsf_min0<<16) |
4623 (msf.cdmsf_sec0<<8) |
4624 msf.cdmsf_frame0;
4625 D_S[d].pos_audio_end = (msf.cdmsf_min1<<16) |
4626 (msf.cdmsf_sec1<<8) |
4627 msf.cdmsf_frame1;
4628 msg(DBG_IOX,"ioctl: CDROMPLAYMSF %08X %08X\n",
4629 D_S[d].pos_audio_start,D_S[d].pos_audio_end);
4630 i=cc_PlayAudio(D_S[d].pos_audio_start,D_S[d].pos_audio_end);
4631 if (i<0)
4632 {
4633 msg(DBG_INF,"ioctl: cc_PlayAudio returns %d\n",i);
4634 DriveReset();
4635 D_S[d].audio_state=0;
4636 RETURN_UP(-EIO);
4637 }
4638 D_S[d].audio_state=audio_playing;
4639 RETURN_UP(0);
4640
4641 case CDROMPLAYTRKIND:
4642 msg(DBG_IOC,"ioctl: CDROMPLAYTRKIND entered.\n");
4643#if SAFE_MIXED
4644 if (D_S[d].has_data>1) RETURN_UP(-EBUSY);
4645#endif
4646 if (D_S[d].audio_state==audio_playing)
4647 {
4648 msg(DBG_IOX,"CDROMPLAYTRKIND: already audio_playing.\n");
4649#if 1
4650 RETURN_UP(0);
4651#else
4652 RETURN_UP(-EINVAL);
4653#endif
4654 }
4655 memcpy(&ti,(void *) arg,sizeof(struct cdrom_ti));
4656 msg(DBG_IOX,"ioctl: trk0: %d, ind0: %d, trk1:%d, ind1:%d\n",
4657 ti.cdti_trk0,ti.cdti_ind0,ti.cdti_trk1,ti.cdti_ind1);
4658 if (ti.cdti_trk0<D_S[d].n_first_track) RETURN_UP(-EINVAL);
4659 if (ti.cdti_trk0>D_S[d].n_last_track) RETURN_UP(-EINVAL);
4660 if (ti.cdti_trk1<ti.cdti_trk0) ti.cdti_trk1=ti.cdti_trk0;
4661 if (ti.cdti_trk1>D_S[d].n_last_track) ti.cdti_trk1=D_S[d].n_last_track;
4662 D_S[d].pos_audio_start=D_S[d].TocBuffer[ti.cdti_trk0].address;
4663 D_S[d].pos_audio_end=D_S[d].TocBuffer[ti.cdti_trk1+1].address;
4664 i=cc_PlayAudio(D_S[d].pos_audio_start,D_S[d].pos_audio_end);
4665 if (i<0)
4666 {
4667 msg(DBG_INF,"ioctl: cc_PlayAudio returns %d\n",i);
4668 DriveReset();
4669 D_S[d].audio_state=0;
4670 RETURN_UP(-EIO);
4671 }
4672 D_S[d].audio_state=audio_playing;
4673 RETURN_UP(0);
4674
4675 case CDROMREADTOCHDR:
4676 msg(DBG_IOC,"ioctl: CDROMREADTOCHDR entered.\n");
4677 tochdr.cdth_trk0=D_S[d].n_first_track;
4678 tochdr.cdth_trk1=D_S[d].n_last_track;
4679 memcpy((void *) arg, &tochdr, sizeof(struct cdrom_tochdr));
4680 RETURN_UP(0);
4681
4682 case CDROMREADTOCENTRY:
4683 msg(DBG_IOC,"ioctl: CDROMREADTOCENTRY entered.\n");
4684 memcpy(&tocentry, (void *) arg, sizeof(struct cdrom_tocentry));
4685 i=tocentry.cdte_track;
4686 if (i==CDROM_LEADOUT) i=D_S[d].n_last_track+1;
4687 else if (i<D_S[d].n_first_track||i>D_S[d].n_last_track)
4688 RETURN_UP(-EINVAL);
4689 tocentry.cdte_adr=D_S[d].TocBuffer[i].ctl_adr&0x0F;
4690 tocentry.cdte_ctrl=(D_S[d].TocBuffer[i].ctl_adr>>4)&0x0F;
4691 tocentry.cdte_datamode=D_S[d].TocBuffer[i].format;
4692 if (tocentry.cdte_format==CDROM_MSF)
4693 {
4694 tocentry.cdte_addr.msf.minute=(D_S[d].TocBuffer[i].address>>16)&0x00FF;
4695 tocentry.cdte_addr.msf.second=(D_S[d].TocBuffer[i].address>>8)&0x00FF;
4696 tocentry.cdte_addr.msf.frame=D_S[d].TocBuffer[i].address&0x00FF;
4697 }
4698 else if (tocentry.cdte_format==CDROM_LBA)
4699 tocentry.cdte_addr.lba=msf2blk(D_S[d].TocBuffer[i].address);
4700 else RETURN_UP(-EINVAL);
4701 memcpy((void *) arg, &tocentry, sizeof(struct cdrom_tocentry));
4702 RETURN_UP(0);
4703
4704 case CDROMSTOP:
4705 msg(DBG_IOC,"ioctl: CDROMSTOP entered.\n");
4706#if SAFE_MIXED
4707 if (D_S[d].has_data>1) RETURN_UP(-EBUSY);
4708#endif
4709 i=cc_Pause_Resume(1);
4710 D_S[d].audio_state=0;
4711#if 0
4712 cc_DriveReset();
4713#endif
4714 RETURN_UP(i);
4715
4716 case CDROMSTART:
4717 msg(DBG_IOC,"ioctl: CDROMSTART entered.\n");
4718 cc_SpinUp();
4719 D_S[d].audio_state=0;
4720 RETURN_UP(0);
4721
4722 case CDROMVOLCTRL:
4723 msg(DBG_IOC,"ioctl: CDROMVOLCTRL entered.\n");
4724 memcpy(&volctrl,(char *) arg,sizeof(volctrl));
4725 D_S[d].vol_chan0=0;
4726 D_S[d].vol_ctrl0=volctrl.channel0;
4727 D_S[d].vol_chan1=1;
4728 D_S[d].vol_ctrl1=volctrl.channel1;
4729 i=cc_SetVolume();
4730 RETURN_UP(0);
4731
4732 case CDROMVOLREAD:
4733 msg(DBG_IOC,"ioctl: CDROMVOLREAD entered.\n");
4734 st=cc_GetVolume();
4735 if (st<0) RETURN_UP(st);
4736 volctrl.channel0=D_S[d].vol_ctrl0;
4737 volctrl.channel1=D_S[d].vol_ctrl1;
4738 volctrl.channel2=0;
4739 volctrl.channel2=0;
4740 memcpy((void *)arg,&volctrl,sizeof(volctrl));
4741 RETURN_UP(0);
4742
4743 case CDROMSUBCHNL:
4744 msg(DBG_IOS,"ioctl: CDROMSUBCHNL entered.\n");
4745
4746
4747
4748
4749
4750
4751 i=cc_ReadSubQ();
4752 if (i<0) {
4753 j=cc_ReadError();
4754 D_S[d].audio_state=CDROM_AUDIO_NO_STATUS;
4755
4756
4757
4758 if (D_S[d].CD_changed==0xFF) {
4759 msg(DBG_000,"Disk changed detect\n");
4760 D_S[d].diskstate_flags &= ~cd_size_bit;
4761 }
4762 RETURN_UP(-EIO);
4763 }
4764 if (D_S[d].CD_changed==0xFF) {
4765
4766 msg(DBG_000,"Disk changed STILL detected, rereading TOC!\n");
4767 i=DiskInfo();
4768 if(i==0) {
4769 D_S[d].CD_changed=0x00;
4770 RETURN_UP(-EIO);
4771 } else {
4772 RETURN_UP(-EIO);
4773 }
4774 }
4775 memcpy(&SC, (void *) arg, sizeof(struct cdrom_subchnl));
4776
4777
4778
4779
4780
4781 cc_ReadStatus();
4782 i=ResponseStatus();
4783 msg(DBG_000,"Drive Status: door_locked =%d.\n", st_door_locked);
4784 msg(DBG_000,"Drive Status: door_closed =%d.\n", st_door_closed);
4785 msg(DBG_000,"Drive Status: caddy_in =%d.\n", st_caddy_in);
4786 msg(DBG_000,"Drive Status: disk_ok =%d.\n", st_diskok);
4787 msg(DBG_000,"Drive Status: spinning =%d.\n", st_spinning);
4788 msg(DBG_000,"Drive Status: busy =%d.\n", st_busy);
4789
4790 switch (D_S[d].audio_state)
4791 {
4792 case audio_playing:
4793 if(st_busy==0) {
4794
4795 D_S[d].audio_state=audio_completed;
4796 SC.cdsc_audiostatus=CDROM_AUDIO_COMPLETED;
4797 } else {
4798 SC.cdsc_audiostatus=CDROM_AUDIO_PLAY;
4799 }
4800 break;
4801 case audio_pausing:
4802 SC.cdsc_audiostatus=CDROM_AUDIO_PAUSED;
4803 break;
4804 case audio_completed:
4805 SC.cdsc_audiostatus=CDROM_AUDIO_COMPLETED;
4806 break;
4807 default:
4808 SC.cdsc_audiostatus=CDROM_AUDIO_NO_STATUS;
4809 break;
4810 }
4811 SC.cdsc_adr=D_S[d].SubQ_ctl_adr;
4812 SC.cdsc_ctrl=D_S[d].SubQ_ctl_adr>>4;
4813 SC.cdsc_trk=bcd2bin(D_S[d].SubQ_trk);
4814 SC.cdsc_ind=bcd2bin(D_S[d].SubQ_pnt_idx);
4815 if (SC.cdsc_format==CDROM_LBA)
4816 {
4817 SC.cdsc_absaddr.lba=msf2blk(D_S[d].SubQ_run_tot);
4818 SC.cdsc_reladdr.lba=msf2blk(D_S[d].SubQ_run_trk);
4819 }
4820 else
4821 {
4822 SC.cdsc_absaddr.msf.minute=(D_S[d].SubQ_run_tot>>16)&0x00FF;
4823 SC.cdsc_absaddr.msf.second=(D_S[d].SubQ_run_tot>>8)&0x00FF;
4824 SC.cdsc_absaddr.msf.frame=D_S[d].SubQ_run_tot&0x00FF;
4825 SC.cdsc_reladdr.msf.minute=(D_S[d].SubQ_run_trk>>16)&0x00FF;
4826 SC.cdsc_reladdr.msf.second=(D_S[d].SubQ_run_trk>>8)&0x00FF;
4827 SC.cdsc_reladdr.msf.frame=D_S[d].SubQ_run_trk&0x00FF;
4828 }
4829 memcpy((void *) arg, &SC, sizeof(struct cdrom_subchnl));
4830 msg(DBG_IOS,"CDROMSUBCHNL: %1X %02X %08X %08X %02X %02X %06X %06X\n",
4831 SC.cdsc_format,SC.cdsc_audiostatus,
4832 SC.cdsc_adr,SC.cdsc_ctrl,
4833 SC.cdsc_trk,SC.cdsc_ind,
4834 SC.cdsc_absaddr,SC.cdsc_reladdr);
4835 RETURN_UP(0);
4836
4837 default:
4838 msg(DBG_IOC,"ioctl: unknown function request %04X\n", cmd);
4839 RETURN_UP(-EINVAL);
4840 }
4841}
4842
4843
4844
4845
4846static void sbp_transfer(struct request *req)
4847{
4848 long offs;
4849
4850 while ( (req->nr_sectors > 0) &&
4851 (req->sector/4 >= D_S[d].sbp_first_frame) &&
4852 (req->sector/4 <= D_S[d].sbp_last_frame) )
4853 {
4854 offs = (req->sector - D_S[d].sbp_first_frame * 4) * 512;
4855 memcpy(req->buffer, D_S[d].sbp_buf + offs, 512);
4856 req->nr_sectors--;
4857 req->sector++;
4858 req->buffer += 512;
4859 }
4860}
4861
4862
4863
4864
4865
4866
4867
4868
4869
4870
4871
4872
4873
4874
4875
4876
4877
4878
4879
4880
4881
4882
4883
4884
4885
4886
4887
4888#undef DEBUG_GTL
4889static inline void sbpcd_end_request(struct request *req, int uptodate) {
4890 list_add(&req->queue, &req->q->queue_head);
4891 end_request(uptodate);
4892}
4893
4894
4895
4896
4897static void DO_SBPCD_REQUEST(request_queue_t * q)
4898{
4899 u_int block;
4900 u_int nsect;
4901 int i, status_tries, data_tries;
4902 struct request *req;
4903#ifdef DEBUG_GTL
4904 static int xx_nr=0;
4905 int xnr;
4906#endif
4907
4908 request_loop:
4909#ifdef DEBUG_GTL
4910 xnr=++xx_nr;
4911
4912 if(QUEUE_EMPTY)
4913 {
4914 printk( "do_sbpcd_request[%di](NULL), Pid:%d, Time:%li\n",
4915 xnr, current->pid, jiffies);
4916 printk( "do_sbpcd_request[%do](NULL) end 0 (null), Time:%li\n",
4917 xnr, jiffies);
4918 CLEAR_INTR;
4919 return;
4920 }
4921
4922 printk(" do_sbpcd_request[%di](%p:%ld+%ld), Pid:%d, Time:%li\n",
4923 xnr, CURRENT, CURRENT->sector, CURRENT->nr_sectors, current->pid, jiffies);
4924#endif
4925 INIT_REQUEST;
4926 req=CURRENT;
4927 blkdev_dequeue_request(req);
4928
4929 if (req->rq_status == RQ_INACTIVE)
4930 sbpcd_end_request(req, 0);
4931 if (req -> sector == -1)
4932 sbpcd_end_request(req, 0);
4933 spin_unlock_irq(&io_request_lock);
4934
4935 down(&ioctl_read_sem);
4936 if (req->cmd != READ)
4937 {
4938 msg(DBG_INF, "bad cmd %d\n", req->cmd);
4939 goto err_done;
4940 }
4941 i = MINOR(req->rq_dev);
4942 if ( (i<0) || (i>=NR_SBPCD) || (D_S[i].drv_id==-1))
4943 {
4944 msg(DBG_INF, "do_request: bad device: %s\n",
4945 kdevname(req->rq_dev));
4946 goto err_done;
4947 }
4948#if OLD_BUSY
4949 while (busy_audio) sbp_sleep(HZ);
4950 busy_data=1;
4951#endif
4952
4953 if (D_S[i].audio_state==audio_playing) goto err_done;
4954 if (d!=i) switch_drive(i);
4955
4956 block = req->sector;
4957 nsect = req->nr_sectors;
4958
4959 msg(DBG_BSZ,"read sector %d (%d sectors)\n", block, nsect);
4960#if 0
4961 msg(DBG_MUL,"read LBA %d\n", block/4);
4962#endif
4963
4964 sbp_transfer(req);
4965
4966 if (req->nr_sectors == 0)
4967 {
4968#ifdef DEBUG_GTL
4969 printk(" do_sbpcd_request[%do](%p:%ld+%ld) end 2, Time:%li\n",
4970 xnr, req, req->sector, req->nr_sectors, jiffies);
4971#endif
4972 up(&ioctl_read_sem);
4973 spin_lock_irq(&io_request_lock);
4974 sbpcd_end_request(req, 1);
4975 goto request_loop;
4976 }
4977
4978#if FUTURE
4979 i=prepare(0,0);
4980 if (i!=0)
4981 msg(DBG_INF,"\"prepare\" tells error %d -- ignored\n", i);
4982#endif
4983
4984 if (!st_spinning) cc_SpinUp();
4985
4986 for (data_tries=n_retries; data_tries > 0; data_tries--)
4987 {
4988 for (status_tries=3; status_tries > 0; status_tries--)
4989 {
4990 flags_cmd_out |= f_respo3;
4991 cc_ReadStatus();
4992 if (sbp_status() != 0) break;
4993 if (st_check) cc_ReadError();
4994 sbp_sleep(1);
4995 }
4996 if (status_tries == 0)
4997 {
4998 msg(DBG_INF,"sbp_status: failed after 3 tries in line %d\n", __LINE__);
4999 break;
5000 }
5001
5002 sbp_read_cmd(req);
5003 sbp_sleep(0);
5004 if (sbp_data(req) != 0)
5005 {
5006#if SAFE_MIXED
5007 D_S[d].has_data=2;
5008#endif
5009#ifdef DEBUG_GTL
5010 printk(" do_sbpcd_request[%do](%p:%ld+%ld) end 3, Time:%li\n",
5011 xnr, req, req->sector, req->nr_sectors, jiffies);
5012#endif
5013 up(&ioctl_read_sem);
5014 spin_lock_irq(&io_request_lock);
5015 sbpcd_end_request(req, 1);
5016 goto request_loop;
5017 }
5018 }
5019
5020 err_done:
5021#if OLD_BUSY
5022 busy_data=0;
5023#endif
5024#ifdef DEBUG_GTL
5025 printk(" do_sbpcd_request[%do](%p:%ld+%ld) end 4 (error), Time:%li\n",
5026 xnr, req, req->sector, req->nr_sectors, jiffies);
5027#endif
5028 up(&ioctl_read_sem);
5029 sbp_sleep(0);
5030 spin_lock_irq(&io_request_lock);
5031 sbpcd_end_request(req, 0);
5032 goto request_loop;
5033}
5034
5035
5036
5037
5038static void sbp_read_cmd(struct request *req)
5039{
5040#undef OLD
5041
5042 int i;
5043 int block;
5044
5045 D_S[d].sbp_first_frame=D_S[d].sbp_last_frame=-1;
5046 D_S[d].sbp_current = 0;
5047 block=req->sector/4;
5048 if (block+D_S[d].sbp_bufsiz <= D_S[d].CDsize_frm)
5049 D_S[d].sbp_read_frames = D_S[d].sbp_bufsiz;
5050 else
5051 {
5052 D_S[d].sbp_read_frames=D_S[d].CDsize_frm-block;
5053
5054 if (D_S[d].sbp_read_frames < 1)
5055 {
5056 msg(DBG_INF,"requested frame %d, CD size %d ???\n",
5057 block, D_S[d].CDsize_frm);
5058 D_S[d].sbp_read_frames=1;
5059 }
5060 }
5061
5062 flags_cmd_out = f_putcmd | f_respo2 | f_ResponseStatus | f_obey_p_check;
5063 clr_cmdbuf();
5064 if (famV_drive)
5065 {
5066 drvcmd[0]=CMDV_READ;
5067 lba2msf(block,&drvcmd[1]);
5068 bin2bcdx(&drvcmd[1]);
5069 bin2bcdx(&drvcmd[2]);
5070 bin2bcdx(&drvcmd[3]);
5071 drvcmd[4]=D_S[d].sbp_read_frames>>8;
5072 drvcmd[5]=D_S[d].sbp_read_frames&0xff;
5073 drvcmd[6]=0x02;
5074 }
5075 else if (fam0L_drive)
5076 {
5077 flags_cmd_out |= f_lopsta | f_getsta | f_bit1;
5078 if (D_S[d].xa_byte==0x20)
5079 {
5080 cmd_type=READ_M2;
5081 drvcmd[0]=CMD0_READ_XA;
5082 drvcmd[1]=(block>>16)&0x0ff;
5083 drvcmd[2]=(block>>8)&0x0ff;
5084 drvcmd[3]=block&0x0ff;
5085 drvcmd[4]=(D_S[d].sbp_read_frames>>8)&0x0ff;
5086 drvcmd[5]=D_S[d].sbp_read_frames&0x0ff;
5087 }
5088 else
5089 {
5090 drvcmd[0]=CMD0_READ;
5091 if (D_S[d].drv_type>=drv_201)
5092 {
5093 lba2msf(block,&drvcmd[1]);
5094 bin2bcdx(&drvcmd[1]);
5095 bin2bcdx(&drvcmd[2]);
5096 bin2bcdx(&drvcmd[3]);
5097 }
5098 else
5099 {
5100 drvcmd[1]=(block>>16)&0x0ff;
5101 drvcmd[2]=(block>>8)&0x0ff;
5102 drvcmd[3]=block&0x0ff;
5103 }
5104 drvcmd[4]=(D_S[d].sbp_read_frames>>8)&0x0ff;
5105 drvcmd[5]=D_S[d].sbp_read_frames&0x0ff;
5106 drvcmd[6]=(D_S[d].drv_type<drv_201)?0:2;
5107 }
5108 }
5109 else if (fam1_drive)
5110 {
5111 drvcmd[0]=CMD1_READ;
5112 lba2msf(block,&drvcmd[1]);
5113 drvcmd[5]=(D_S[d].sbp_read_frames>>8)&0x0ff;
5114 drvcmd[6]=D_S[d].sbp_read_frames&0x0ff;
5115 }
5116 else if (fam2_drive)
5117 {
5118 drvcmd[0]=CMD2_READ;
5119 lba2msf(block,&drvcmd[1]);
5120 drvcmd[4]=(D_S[d].sbp_read_frames>>8)&0x0ff;
5121 drvcmd[5]=D_S[d].sbp_read_frames&0x0ff;
5122 drvcmd[6]=0x02;
5123 }
5124 else if (famT_drive)
5125 {
5126 drvcmd[0]=CMDT_READ;
5127 drvcmd[2]=(block>>24)&0x0ff;
5128 drvcmd[3]=(block>>16)&0x0ff;
5129 drvcmd[4]=(block>>8)&0x0ff;
5130 drvcmd[5]=block&0x0ff;
5131 drvcmd[7]=(D_S[d].sbp_read_frames>>8)&0x0ff;
5132 drvcmd[8]=D_S[d].sbp_read_frames&0x0ff;
5133 }
5134 flags_cmd_out=f_putcmd;
5135 response_count=0;
5136 i=cmd_out();
5137 if (i<0) msg(DBG_INF,"error giving READ command: %0d\n", i);
5138 return;
5139}
5140
5141
5142
5143
5144
5145static int sbp_data(struct request *req)
5146{
5147 int i=0, j=0, l, frame;
5148 u_int try=0;
5149 u_long timeout;
5150 u_char *p;
5151 u_int data_tries = 0;
5152 u_int data_waits = 0;
5153 u_int data_retrying = 0;
5154 int error_flag;
5155 int xa_count;
5156 int max_latency;
5157 int success;
5158 int wait;
5159 int duration;
5160
5161 error_flag=0;
5162 success=0;
5163#if LONG_TIMING
5164 max_latency=9*HZ;
5165#else
5166 if (D_S[d].f_multisession) max_latency=15*HZ;
5167 else max_latency=5*HZ;
5168#endif
5169 duration=jiffies;
5170 for (frame=0;frame<D_S[d].sbp_read_frames&&!error_flag; frame++)
5171 {
5172 SBPCD_CLI;
5173
5174 del_timer(&data_timer);
5175 data_timer.expires=jiffies+max_latency;
5176 timed_out_data=0;
5177 add_timer(&data_timer);
5178 while (!timed_out_data)
5179 {
5180 if (D_S[d].f_multisession) try=maxtim_data*4;
5181 else try=maxtim_data;
5182 msg(DBG_000,"sbp_data: CDi_status loop: try=%d.\n",try);
5183 for ( ; try!=0;try--)
5184 {
5185 j=inb(CDi_status);
5186 if (!(j&s_not_data_ready)) break;;
5187 if (!(j&s_not_result_ready)) break;
5188 if (fam0LV_drive) if (j&s_attention) break;
5189 }
5190 if (!(j&s_not_data_ready)) goto data_ready;
5191 if (try==0)
5192 {
5193 if (data_retrying == 0) data_waits++;
5194 data_retrying = 1;
5195 msg(DBG_000,"sbp_data: CDi_status loop: sleeping.\n");
5196 sbp_sleep(1);
5197 try = 1;
5198 }
5199 }
5200 msg(DBG_INF,"sbp_data: CDi_status loop expired.\n");
5201 data_ready:
5202 del_timer(&data_timer);
5203
5204 if (timed_out_data)
5205 {
5206 msg(DBG_INF,"sbp_data: CDi_status timeout (timed_out_data) (%02X).\n", j);
5207 error_flag++;
5208 }
5209 if (try==0)
5210 {
5211 msg(DBG_INF,"sbp_data: CDi_status timeout (try=0) (%02X).\n", j);
5212 error_flag++;
5213 }
5214 if (!(j&s_not_result_ready))
5215 {
5216 msg(DBG_INF, "sbp_data: RESULT_READY where DATA_READY awaited (%02X).\n", j);
5217 response_count=20;
5218 j=ResponseInfo();
5219 j=inb(CDi_status);
5220 }
5221 if (j&s_not_data_ready)
5222 {
5223 if ((D_S[d].ored_ctl_adr&0x40)==0)
5224 msg(DBG_INF, "CD contains no data tracks.\n");
5225 else msg(DBG_INF, "sbp_data: DATA_READY timeout (%02X).\n", j);
5226 error_flag++;
5227 }
5228 SBPCD_STI;
5229 if (error_flag) break;
5230
5231 msg(DBG_000, "sbp_data: beginning to read.\n");
5232 p = D_S[d].sbp_buf + frame * CD_FRAMESIZE;
5233 if (sbpro_type==1) OUT(CDo_sel_i_d,1);
5234 if (cmd_type==READ_M2) {
5235 if (do_16bit) insw(CDi_data, xa_head_buf, CD_XA_HEAD>>1);
5236 else insb(CDi_data, xa_head_buf, CD_XA_HEAD);
5237 }
5238 if (do_16bit) insw(CDi_data, p, CD_FRAMESIZE>>1);
5239 else insb(CDi_data, p, CD_FRAMESIZE);
5240 if (cmd_type==READ_M2) {
5241 if (do_16bit) insw(CDi_data, xa_tail_buf, CD_XA_TAIL>>1);
5242 else insb(CDi_data, xa_tail_buf, CD_XA_TAIL);
5243 }
5244 D_S[d].sbp_current++;
5245 if (sbpro_type==1) OUT(CDo_sel_i_d,0);
5246 if (cmd_type==READ_M2)
5247 {
5248 for (xa_count=0;xa_count<CD_XA_HEAD;xa_count++)
5249 sprintf(&msgbuf[xa_count*3], " %02X", xa_head_buf[xa_count]);
5250 msgbuf[xa_count*3]=0;
5251 msg(DBG_XA1,"xa head:%s\n", msgbuf);
5252 }
5253 data_retrying = 0;
5254 data_tries++;
5255 if (data_tries >= 1000)
5256 {
5257 msg(DBG_INF,"sbp_data() statistics: %d waits in %d frames.\n", data_waits, data_tries);
5258 data_waits = data_tries = 0;
5259 }
5260 }
5261 duration=jiffies-duration;
5262 msg(DBG_TEA,"time to read %d frames: %d jiffies .\n",frame,duration);
5263 if (famT_drive)
5264 {
5265 wait=8;
5266 do
5267 {
5268 if (teac==2)
5269 {
5270 if ((i=CDi_stat_loop_T()) == -1) break;
5271 }
5272 else
5273 {
5274 sbp_sleep(1);
5275 OUT(CDo_sel_i_d,0);
5276 i=inb(CDi_status);
5277 }
5278 if (!(i&s_not_data_ready))
5279 {
5280 OUT(CDo_sel_i_d,1);
5281 j=0;
5282 do
5283 {
5284 if (do_16bit) i=inw(CDi_data);
5285 else i=inb(CDi_data);
5286 j++;
5287 i=inb(CDi_status);
5288 }
5289 while (!(i&s_not_data_ready));
5290 msg(DBG_TEA, "==========too much data (%d bytes/words)==============.\n", j);
5291 }
5292 if (!(i&s_not_result_ready))
5293 {
5294 OUT(CDo_sel_i_d,0);
5295 l=0;
5296 do
5297 {
5298 infobuf[l++]=inb(CDi_info);
5299 i=inb(CDi_status);
5300 }
5301 while (!(i&s_not_result_ready));
5302 if (infobuf[0]==0x00) success=1;
5303#if 1
5304 for (j=0;j<l;j++) sprintf(&msgbuf[j*3], " %02X", infobuf[j]);
5305 msgbuf[j*3]=0;
5306 msg(DBG_TEA,"sbp_data info response:%s\n", msgbuf);
5307#endif
5308 if (infobuf[0]==0x02)
5309 {
5310 error_flag++;
5311 do
5312 {
5313 ++recursion;
5314 if (recursion>1) msg(DBG_TEA,"cmd_out_T READ_ERR recursion (sbp_data): %d !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n",recursion);
5315 else msg(DBG_TEA,"sbp_data: CMDT_READ_ERR necessary.\n");
5316 clr_cmdbuf();
5317 drvcmd[0]=CMDT_READ_ERR;
5318 j=cmd_out_T();
5319 --recursion;
5320 sbp_sleep(1);
5321 }
5322 while (j<0);
5323 D_S[d].error_state=infobuf[2];
5324 D_S[d].b3=infobuf[3];
5325 D_S[d].b4=infobuf[4];
5326 }
5327 break;
5328 }
5329 else
5330 {
5331#if 0
5332 msg(DBG_TEA, "============= waiting for result=================.\n");
5333 sbp_sleep(1);
5334#endif
5335 }
5336 }
5337 while (wait--);
5338 }
5339
5340 if (error_flag)
5341 {
5342 msg(DBG_TEA, "================error flag: %d=================.\n", error_flag);
5343 msg(DBG_INF,"sbp_data: read aborted by drive.\n");
5344#if 1
5345 i=cc_DriveReset();
5346#else
5347 i=cc_ReadError();
5348#endif
5349 return (0);
5350 }
5351
5352 if (fam0LV_drive)
5353 {
5354 SBPCD_CLI;
5355 i=maxtim_data;
5356 for (timeout=jiffies+HZ; time_before(jiffies, timeout); timeout--)
5357 {
5358 for ( ;i!=0;i--)
5359 {
5360 j=inb(CDi_status);
5361 if (!(j&s_not_data_ready)) break;
5362 if (!(j&s_not_result_ready)) break;
5363 if (j&s_attention) break;
5364 }
5365 if (i != 0 || time_after_eq(jiffies, timeout)) break;
5366 sbp_sleep(0);
5367 i = 1;
5368 }
5369 if (i==0) msg(DBG_INF,"status timeout after READ.\n");
5370 if (!(j&s_attention))
5371 {
5372 msg(DBG_INF,"sbp_data: timeout waiting DRV_ATTN - retrying.\n");
5373 i=cc_DriveReset();
5374 SBPCD_STI;
5375 return (0);
5376 }
5377 SBPCD_STI;
5378 }
5379
5380#if 0
5381 if (!success)
5382#endif
5383 do
5384 {
5385 if (fam0LV_drive) cc_ReadStatus();
5386#if 1
5387 if (famT_drive) msg(DBG_TEA, "================before ResponseStatus=================.\n", i);
5388#endif
5389 i=ResponseStatus();
5390#if 1
5391 if (famT_drive) msg(DBG_TEA, "================ResponseStatus: %d=================.\n", i);
5392#endif
5393 if (i<0)
5394 {
5395 msg(DBG_INF,"bad cc_ReadStatus after read: %02X\n", D_S[d].status_bits);
5396 return (0);
5397 }
5398 }
5399 while ((fam0LV_drive)&&(!st_check)&&(!(i&p_success)));
5400 if (st_check)
5401 {
5402 i=cc_ReadError();
5403 msg(DBG_INF,"cc_ReadError was necessary after read: %d\n",i);
5404 return (0);
5405 }
5406 if (fatal_err)
5407 {
5408 fatal_err=0;
5409 D_S[d].sbp_first_frame=D_S[d].sbp_last_frame=-1;
5410 D_S[d].sbp_current = 0;
5411 msg(DBG_INF,"sbp_data: fatal_err - retrying.\n");
5412 return (0);
5413 }
5414
5415 D_S[d].sbp_first_frame = req -> sector / 4;
5416 D_S[d].sbp_last_frame = D_S[d].sbp_first_frame + D_S[d].sbp_read_frames - 1;
5417 sbp_transfer(req);
5418 return (1);
5419}
5420
5421
5422static struct block_device_operations sbpcd_bdops =
5423{
5424 owner: THIS_MODULE,
5425 open: cdrom_open,
5426 release: cdrom_release,
5427 ioctl: cdrom_ioctl,
5428 check_media_change: cdrom_media_changed,
5429};
5430
5431
5432
5433
5434static int sbpcd_open(struct cdrom_device_info *cdi, int purpose)
5435{
5436 int i;
5437
5438 i = MINOR(cdi->dev);
5439
5440 down(&ioctl_read_sem);
5441 switch_drive(i);
5442
5443
5444
5445
5446 msg(DBG_LCK,"open_count: %d -> %d\n",
5447 D_S[d].open_count,D_S[d].open_count+1);
5448 if (++D_S[d].open_count<=1)
5449 {
5450 i=LockDoor();
5451 D_S[d].open_count=1;
5452 if (famT_drive) msg(DBG_TEA,"sbpcd_open: before i=DiskInfo();.\n");
5453 i=DiskInfo();
5454 if (famT_drive) msg(DBG_TEA,"sbpcd_open: after i=DiskInfo();.\n");
5455 if ((D_S[d].ored_ctl_adr&0x40)==0)
5456 {
5457 msg(DBG_INF,"CD contains no data tracks.\n");
5458#if SAFE_MIXED
5459 D_S[d].has_data=0;
5460#endif
5461 }
5462#if SAFE_MIXED
5463 else if (D_S[d].has_data<1) D_S[d].has_data=1;
5464#endif
5465 }
5466 if (!st_spinning) cc_SpinUp();
5467 RETURN_UP(0);
5468}
5469
5470
5471
5472
5473static void sbpcd_release(struct cdrom_device_info * cdi)
5474{
5475 int i;
5476
5477 i = MINOR(cdi->dev);
5478 if ((i<0) || (i>=NR_SBPCD) || (D_S[i].drv_id==-1))
5479 {
5480 msg(DBG_INF, "release: bad device: %04X\n", cdi->dev);
5481 return ;
5482 }
5483 down(&ioctl_read_sem);
5484 switch_drive(i);
5485
5486
5487
5488 msg(DBG_LCK,"open_count: %d -> %d\n",
5489 D_S[d].open_count,D_S[d].open_count-1);
5490 if (D_S[d].open_count>-2)
5491 {
5492 if (--D_S[d].open_count<=0)
5493 {
5494 D_S[d].sbp_first_frame=D_S[d].sbp_last_frame=-1;
5495 invalidate_buffers(cdi->dev);
5496 if (D_S[d].audio_state!=audio_playing)
5497 if (D_S[d].f_eject) cc_SpinDown();
5498 D_S[d].diskstate_flags &= ~cd_size_bit;
5499 D_S[d].open_count=0;
5500#if SAFE_MIXED
5501 D_S[d].has_data=0;
5502#endif
5503 }
5504 }
5505 up(&ioctl_read_sem);
5506 return ;
5507}
5508
5509
5510
5511
5512static int sbpcd_media_changed( struct cdrom_device_info *cdi, int disc_nr);
5513static struct cdrom_device_ops sbpcd_dops = {
5514 open: sbpcd_open,
5515 release: sbpcd_release,
5516 drive_status: sbpcd_drive_status,
5517 media_changed: sbpcd_media_changed,
5518 tray_move: sbpcd_tray_move,
5519 lock_door: sbpcd_lock_door,
5520 select_speed: sbpcd_select_speed,
5521 get_last_session: sbpcd_get_last_session,
5522 get_mcn: sbpcd_get_mcn,
5523 reset: sbpcd_reset,
5524 audio_ioctl: sbpcd_audio_ioctl,
5525 dev_ioctl: sbpcd_dev_ioctl,
5526 capability: CDC_CLOSE_TRAY | CDC_OPEN_TRAY | CDC_LOCK |
5527 CDC_MULTI_SESSION | CDC_MEDIA_CHANGED |
5528 CDC_MCN | CDC_PLAY_AUDIO | CDC_IOCTLS,
5529 n_minors: 1,
5530};
5531
5532static struct cdrom_device_info sbpcd_info = {
5533 ops: &sbpcd_dops,
5534 speed: 2,
5535 capacity: 1,
5536 name: "sbpcd",
5537};
5538
5539
5540
5541
5542
5543
5544
5545
5546
5547
5548
5549
5550
5551
5552
5553
5554
5555
5556
5557
5558
5559
5560
5561
5562
5563
5564
5565
5566#if (SBPCD_ISSUE-1)
5567static int sbpcd_setup(char *s)
5568#else
5569int sbpcd_setup(char *s)
5570#endif
5571{
5572#ifndef MODULE
5573 int p[4];
5574 (void)get_options(s, ARRAY_SIZE(p), p);
5575 setup_done++;
5576 msg(DBG_INI,"sbpcd_setup called with %04X,%s\n",p[1], s);
5577 sbpro_type=0;
5578 if (p[0]>1) sbpro_type=p[2];
5579 else if (!strcmp(s,str_sb)) sbpro_type=1;
5580 else if (!strcmp(s,str_sb_l)) sbpro_type=1;
5581 else if (!strcmp(s,str_sp)) sbpro_type=2;
5582 else if (!strcmp(s,str_sp_l)) sbpro_type=2;
5583 else if (!strcmp(s,str_ss)) sbpro_type=2;
5584 else if (!strcmp(s,str_ss_l)) sbpro_type=2;
5585 else if (!strcmp(s,str_t16)) sbpro_type=3;
5586 else if (!strcmp(s,str_t16_l)) sbpro_type=3;
5587 if (p[0]>0) sbpcd_ioaddr=p[1];
5588 if (p[0]>2) max_drives=p[3];
5589#else
5590 sbpcd_ioaddr = sbpcd[0];
5591 sbpro_type = sbpcd[1];
5592#endif
5593
5594 CDo_command=sbpcd_ioaddr;
5595 CDi_info=sbpcd_ioaddr;
5596 CDi_status=sbpcd_ioaddr+1;
5597 CDo_sel_i_d=sbpcd_ioaddr+1;
5598 CDo_reset=sbpcd_ioaddr+2;
5599 CDo_enable=sbpcd_ioaddr+3;
5600 f_16bit=0;
5601 if ((sbpro_type==1)||(sbpro_type==3))
5602 {
5603 CDi_data=sbpcd_ioaddr;
5604 if (sbpro_type==3)
5605 {
5606 f_16bit=1;
5607 sbpro_type=1;
5608 }
5609 }
5610 else CDi_data=sbpcd_ioaddr+2;
5611
5612 return 1;
5613}
5614
5615__setup("sbpcd=", sbpcd_setup);
5616
5617
5618
5619
5620
5621
5622
5623
5624
5625
5626
5627
5628
5629
5630
5631
5632
5633
5634
5635static int __init config_spea(void)
5636{
5637
5638
5639
5640
5641
5642
5643
5644
5645 int n_ports=0x10;
5646
5647 int irq_number=0;
5648 int dma_channel=0;
5649 int dack_polarity=0;
5650 int drq_polarity=0x40;
5651 int i;
5652
5653#define SPEA_REG_1 sbpcd_ioaddr-0x08+4
5654#define SPEA_REG_2 sbpcd_ioaddr-0x08+5
5655
5656 OUT(SPEA_REG_1,0xFF);
5657 i=inb(SPEA_REG_1);
5658 if (i!=0x0F)
5659 {
5660 msg(DBG_SEQ,"no SPEA interface at %04X present.\n", sbpcd_ioaddr);
5661 return (-1);
5662 }
5663 OUT(SPEA_REG_1,0x04);
5664 OUT(SPEA_REG_2,0xC0);
5665
5666 OUT(SPEA_REG_1,0x05);
5667 OUT(SPEA_REG_2,0x10|drq_polarity|dack_polarity);
5668
5669#if 1
5670#define SPEA_PATTERN 0x80
5671#else
5672#define SPEA_PATTERN 0x00
5673#endif
5674 OUT(SPEA_REG_1,0x06);
5675 OUT(SPEA_REG_2,dma_channel|irq_number|SPEA_PATTERN);
5676 OUT(SPEA_REG_2,dma_channel|irq_number|SPEA_PATTERN);
5677
5678 OUT(SPEA_REG_1,0x09);
5679 i=(inb(SPEA_REG_2)&0xCF)|n_ports;
5680 OUT(SPEA_REG_2,i);
5681
5682 sbpro_type = 0;
5683 msg(DBG_SEQ,"found SoundScape interface at %04X.\n", sbpcd_ioaddr);
5684 return (0);
5685}
5686
5687#ifdef DONT_MERGE_REQUESTS
5688static int dont_merge_requests_fn(request_queue_t *q, struct request *req,
5689 struct request *next, int max_segments)
5690{
5691 return 0;
5692}
5693
5694static int dont_bh_merge_fn(request_queue_t *q, struct request *req,
5695 struct buffer_head *bh, int max_segments)
5696{
5697 return 0;
5698}
5699#endif
5700
5701
5702
5703
5704
5705
5706
5707static devfs_handle_t devfs_handle;
5708
5709#ifdef MODULE
5710int __init __SBPCD_INIT(void)
5711#else
5712int __init SBPCD_INIT(void)
5713#endif
5714{
5715 char nbuff[16];
5716 int i=0, j=0;
5717 int addr[2]={1, CDROM_PORT};
5718 int port_index;
5719
5720 sti();
5721
5722 msg(DBG_INF,"sbpcd.c %s\n", VERSION);
5723#ifndef MODULE
5724#if DISTRIBUTION
5725 if (!setup_done)
5726 {
5727 msg(DBG_INF,"Looking for Matsushita/Panasonic, CreativeLabs, Longshine, TEAC CD-ROM drives\n");
5728 msg(DBG_INF,"= = = = = = = = = = W A R N I N G = = = = = = = = = =\n");
5729 msg(DBG_INF,"Auto-Probing can cause a hang (f.e. touching an NE2000 card).\n");
5730 msg(DBG_INF,"If that happens, you have to reboot and use the\n");
5731 msg(DBG_INF,"LILO (kernel) command line feature like:\n");
5732 msg(DBG_INF," LILO boot: ... sbpcd=0x230,SoundBlaster\n");
5733 msg(DBG_INF,"or like:\n");
5734 msg(DBG_INF," LILO boot: ... sbpcd=0x300,LaserMate\n");
5735 msg(DBG_INF,"or like:\n");
5736 msg(DBG_INF," LILO boot: ... sbpcd=0x338,SoundScape\n");
5737 msg(DBG_INF,"with your REAL address.\n");
5738 msg(DBG_INF,"= = = = = = = = = = END of WARNING = = = = = == = = =\n");
5739 }
5740#endif
5741 sbpcd[0]=sbpcd_ioaddr;
5742 sbpcd[1]=sbpro_type;
5743#endif
5744
5745 for (port_index=0;port_index<NUM_PROBE;port_index+=2)
5746 {
5747 addr[1]=sbpcd[port_index];
5748 if (addr[1]==0) break;
5749 if (check_region(addr[1],4))
5750 {
5751 msg(DBG_INF,"check_region: %03X is not free.\n",addr[1]);
5752 continue;
5753 }
5754 if (sbpcd[port_index+1]==2) type=str_sp;
5755 else if (sbpcd[port_index+1]==1) type=str_sb;
5756 else if (sbpcd[port_index+1]==3) type=str_t16;
5757 else type=str_lm;
5758 sbpcd_setup((char *)type);
5759#if DISTRIBUTION
5760 msg(DBG_INF,"Scanning 0x%X (%s)...\n", CDo_command, type);
5761#endif
5762 if (sbpcd[port_index+1]==2)
5763 {
5764 i=config_spea();
5765 if (i<0) continue;
5766 }
5767#ifdef PATH_CHECK
5768 if (check_card(addr[1])) continue;
5769#endif
5770 i=check_drives();
5771 msg(DBG_INI,"check_drives done.\n");
5772 if (i>=0) break;
5773 }
5774
5775 if (ndrives==0)
5776 {
5777 msg(DBG_INF, "No drive found.\n");
5778#ifdef MODULE
5779 return -EIO;
5780#else
5781 goto init_done;
5782#endif
5783 }
5784
5785 if (port_index>0)
5786 {
5787 msg(DBG_INF, "You should read linux/Documentation/cdrom/sbpcd\n");
5788 msg(DBG_INF, "and then configure sbpcd.h for your hardware.\n");
5789 }
5790 check_datarate();
5791 msg(DBG_INI,"check_datarate done.\n");
5792
5793 for (j=0;j<NR_SBPCD;j++)
5794 {
5795 if (D_S[j].drv_id==-1) continue;
5796 switch_drive(j);
5797#if 1
5798 if (!famL_drive) cc_DriveReset();
5799#endif
5800 if (!st_spinning) cc_SpinUp();
5801 D_S[j].sbp_first_frame = -1;
5802 D_S[j].sbp_last_frame = -1;
5803 D_S[j].sbp_read_frames = 0;
5804 D_S[j].sbp_current = 0;
5805 D_S[j].CD_changed=1;
5806 D_S[j].frame_size=CD_FRAMESIZE;
5807 D_S[j].f_eject=0;
5808#if EJECT
5809 if (!fam0_drive) D_S[j].f_eject=1;
5810#endif
5811 cc_ReadStatus();
5812 i=ResponseStatus();
5813 if (famT_drive) i=ResponseStatus();
5814 if (i<0)
5815 {
5816 if (i!=-402)
5817 msg(DBG_INF,"init: ResponseStatus returns %d.\n",i);
5818 }
5819 else
5820 {
5821 if (st_check)
5822 {
5823 i=cc_ReadError();
5824 msg(DBG_INI,"init: cc_ReadError returns %d\n",i);
5825 }
5826 }
5827 msg(DBG_INI,"init: first GetStatus: %d\n",i);
5828 msg(DBG_LCS,"init: first GetStatus: error_byte=%d\n",
5829 D_S[j].error_byte);
5830 if (D_S[j].error_byte==aud_12)
5831 {
5832 timeout=jiffies+2*HZ;
5833 do
5834 {
5835 i=GetStatus();
5836 msg(DBG_INI,"init: second GetStatus: %02X\n",i);
5837 msg(DBG_LCS,
5838 "init: second GetStatus: error_byte=%d\n",
5839 D_S[j].error_byte);
5840 if (i<0) break;
5841 if (!st_caddy_in) break;
5842 }
5843 while ((!st_diskok)||time_after(jiffies, timeout));
5844 }
5845 i=SetSpeed();
5846 if (i>=0) D_S[j].CD_changed=1;
5847 }
5848
5849
5850
5851
5852
5853#if SOUND_BASE
5854 OUT(MIXER_addr,MIXER_CD_Volume);
5855 OUT(MIXER_data,0xCC);
5856#endif
5857
5858 if (devfs_register_blkdev(MAJOR_NR, major_name, &sbpcd_bdops) != 0)
5859 {
5860 msg(DBG_INF, "Can't get MAJOR %d for Matsushita CDROM\n", MAJOR_NR);
5861#ifdef MODULE
5862 return -EIO;
5863#else
5864 goto init_done;
5865#endif
5866 }
5867 blk_init_queue(BLK_DEFAULT_QUEUE(MAJOR_NR), DEVICE_REQUEST);
5868#ifdef DONT_MERGE_REQUESTS
5869 (BLK_DEFAULT_QUEUE(MAJOR_NR))->back_merge_fn = dont_bh_merge_fn;
5870 (BLK_DEFAULT_QUEUE(MAJOR_NR))->front_merge_fn = dont_bh_merge_fn;
5871 (BLK_DEFAULT_QUEUE(MAJOR_NR))->merge_requests_fn = dont_merge_requests_fn;
5872#endif
5873 blk_queue_headactive(BLK_DEFAULT_QUEUE(MAJOR_NR), 0);
5874 read_ahead[MAJOR_NR] = buffers * (CD_FRAMESIZE / 512);
5875
5876 request_region(CDo_command,4,major_name);
5877
5878 devfs_handle = devfs_mk_dir (NULL, "sbp", NULL);
5879 for (j=0;j<NR_SBPCD;j++)
5880 {
5881 struct cdrom_device_info * sbpcd_infop;
5882
5883 if (D_S[j].drv_id==-1) continue;
5884 switch_drive(j);
5885#if SAFE_MIXED
5886 D_S[j].has_data=0;
5887#endif
5888
5889
5890
5891 D_S[j].aud_buf=NULL;
5892 D_S[j].sbp_audsiz=0;
5893 D_S[j].sbp_bufsiz=buffers;
5894 if (D_S[j].drv_type&drv_fam1)
5895 if (READ_AUDIO>0) D_S[j].sbp_audsiz=READ_AUDIO;
5896 D_S[j].sbp_buf=(u_char *) vmalloc(D_S[j].sbp_bufsiz*CD_FRAMESIZE);
5897 if (D_S[j].sbp_buf==NULL)
5898 {
5899 msg(DBG_INF,"data buffer (%d frames) not available.\n",D_S[j].sbp_bufsiz);
5900 if ((devfs_unregister_blkdev(MAJOR_NR, major_name) == -EINVAL))
5901 {
5902 printk("Can't unregister %s\n", major_name);
5903 }
5904 release_region(CDo_command,4);
5905 blk_cleanup_queue(BLK_DEFAULT_QUEUE(MAJOR_NR));
5906 return -EIO;
5907 }
5908#ifdef MODULE
5909 msg(DBG_INF,"data buffer size: %d frames.\n",buffers);
5910#endif
5911 if (D_S[j].sbp_audsiz>0)
5912 {
5913 D_S[j].aud_buf=(u_char *) vmalloc(D_S[j].sbp_audsiz*CD_FRAMESIZE_RAW);
5914 if (D_S[j].aud_buf==NULL) msg(DBG_INF,"audio buffer (%d frames) not available.\n",D_S[j].sbp_audsiz);
5915 else msg(DBG_INF,"audio buffer size: %d frames.\n",D_S[j].sbp_audsiz);
5916 }
5917 sbpcd_infop = vmalloc(sizeof (struct cdrom_device_info));
5918 if (sbpcd_infop == NULL)
5919 {
5920 release_region(CDo_command,4);
5921 blk_cleanup_queue(BLK_DEFAULT_QUEUE(MAJOR_NR));
5922 return -ENOMEM;
5923 }
5924 D_S[j].sbpcd_infop = sbpcd_infop;
5925 memcpy (sbpcd_infop, &sbpcd_info, sizeof(struct cdrom_device_info));
5926 sbpcd_infop->dev = MKDEV(MAJOR_NR, j);
5927 strncpy(sbpcd_infop->name,major_name, sizeof(sbpcd_infop->name));
5928
5929 sprintf (nbuff, "c%dt%d/cd", SBPCD_ISSUE - 1, D_S[j].drv_id);
5930 sbpcd_infop->de =
5931 devfs_register (devfs_handle, nbuff, DEVFS_FL_DEFAULT,
5932 MAJOR_NR, j, S_IFBLK | S_IRUGO | S_IWUGO,
5933 &sbpcd_bdops, NULL);
5934 if (register_cdrom(sbpcd_infop))
5935 {
5936 printk(" sbpcd: Unable to register with Uniform CD-ROm driver\n");
5937 }
5938
5939
5940
5941 sbpcd_blocksizes[j]=CD_FRAMESIZE;
5942 }
5943 blksize_size[MAJOR_NR]=sbpcd_blocksizes;
5944
5945#ifndef MODULE
5946 init_done:
5947#if !(SBPCD_ISSUE-1)
5948#ifdef CONFIG_SBPCD2
5949 sbpcd2_init();
5950#endif
5951#ifdef CONFIG_SBPCD3
5952 sbpcd3_init();
5953#endif
5954#ifdef CONFIG_SBPCD4
5955 sbpcd4_init();
5956#endif
5957#endif
5958#endif
5959 return 0;
5960}
5961
5962#ifdef MODULE
5963void sbpcd_exit(void)
5964{
5965 int j;
5966
5967 if ((devfs_unregister_blkdev(MAJOR_NR, major_name) == -EINVAL))
5968 {
5969 msg(DBG_INF, "What's that: can't unregister %s.\n", major_name);
5970 return;
5971 }
5972 release_region(CDo_command,4);
5973 blk_cleanup_queue(BLK_DEFAULT_QUEUE(MAJOR_NR));
5974 devfs_unregister (devfs_handle);
5975 for (j=0;j<NR_SBPCD;j++)
5976 {
5977 if (D_S[j].drv_id==-1) continue;
5978 vfree(D_S[j].sbp_buf);
5979 if (D_S[j].sbp_audsiz>0) vfree(D_S[j].aud_buf);
5980 if ((unregister_cdrom(D_S[j].sbpcd_infop) == -EINVAL))
5981 {
5982 msg(DBG_INF, "What's that: can't unregister info %s.\n", major_name);
5983 return;
5984 }
5985 vfree(D_S[j].sbpcd_infop);
5986 }
5987 msg(DBG_INF, "%s module released.\n", major_name);
5988}
5989
5990
5991#ifdef MODULE
5992module_init(__SBPCD_INIT) ;
5993#endif
5994module_exit(sbpcd_exit);
5995
5996
5997#endif
5998
5999
6000
6001
6002
6003static int sbpcd_chk_disk_change(kdev_t full_dev)
6004{
6005 int i;
6006
6007 msg(DBG_CHK,"media_check (%d) called\n", MINOR(full_dev));
6008 i=MINOR(full_dev);
6009
6010 if (D_S[i].CD_changed==0xFF)
6011 {
6012 D_S[i].CD_changed=0;
6013 msg(DBG_CHK,"medium changed (drive %d)\n", i);
6014
6015 invalidate_buffers(full_dev);
6016 D_S[d].diskstate_flags &= ~toc_bit;
6017 D_S[d].diskstate_flags &= ~cd_size_bit;
6018#if SAFE_MIXED
6019 D_S[d].has_data=0;
6020#endif
6021
6022 return (1);
6023 }
6024 else
6025 return (0);
6026}
6027
6028static int sbpcd_media_changed( struct cdrom_device_info *cdi, int disc_nr)
6029{
6030 return sbpcd_chk_disk_change(cdi->dev);
6031}
6032
6033MODULE_LICENSE("GPL");
6034
6035
6036
6037
6038
6039
6040
6041
6042
6043
6044
6045
6046
6047
6048
6049
6050
6051
6052
6053