~ubuntu-branches/ubuntu/vivid/sg3-utils/vivid-proposed

« back to all changes in this revision

Viewing changes to lib/sg_lib.c

  • Committer: Package Import Robot
  • Author(s): Ritesh Raj Sarraf
  • Date: 2013-06-23 16:08:01 UTC
  • mfrom: (1.2.7)
  • Revision ID: package-import@ubuntu.com-20130623160801-7rt7zb2dwk0ba7ut
Tags: 1.36-1
* [69e9dac] Imported Upstream version 1.36
* [cb75936] Add debian compat, level 7
* [68fed25] update README.source
* [3c724fc] Add build-dep autotools-dev
* [e4b9fdd] add destdir to install path
* [7cfff11] Simplify build with debhelper
* [f9a7540] Update symbols for 1.36 release
* [7b0b48d] Enable hardening build

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
1
/*
2
 
 * Copyright (c) 1999-2011 Douglas Gilbert.
 
2
 * Copyright (c) 1999-2013 Douglas Gilbert.
3
3
 * All rights reserved.
4
4
 * Use of this source code is governed by a BSD-style
5
5
 * license that can be found in the BSD_LICENSE file.
29
29
 
30
30
#include <stdio.h>
31
31
#include <stdlib.h>
 
32
#include <stdarg.h>
32
33
#include <string.h>
33
34
#include <ctype.h>
34
35
#define __STDC_FORMAT_MACROS 1
41
42
#include "config.h"
42
43
#endif
43
44
 
 
45
/* sg_lib_version_str (and datestamp) defined in sg_lib_data.c file */
 
46
 
 
47
#define ASCQ_ATA_PT_INFO_AVAILABLE 0x1d  /* corresponding ASC is 0 */
44
48
 
45
49
FILE * sg_warnings_strm = NULL;        /* would like to default to stderr */
46
50
 
48
52
static void dStrHexErr(const char* str, int len, int b_len, char * b);
49
53
 
50
54
 
 
55
/* Want safe, 'n += snprintf(b + n, blen - n, ...)' style sequence of
 
56
 * functions. Returns number number of chars placed in cp excluding the
 
57
 * trailing null char. So for cp_max_len > 0 the return value is always
 
58
 * < cp_max_len; for cp_max_len <= 1 the return value is 0 and no chars
 
59
 * are written to cp. Note this means that when cp_max_len = 1, this
 
60
 * function assumes that cp[0] is the null character and does nothing
 
61
 * (and returns 0).  */
 
62
static int
 
63
my_snprintf(char * cp, int cp_max_len, const char * fmt, ...)
 
64
{
 
65
    va_list args;
 
66
    int n;
 
67
 
 
68
    if (cp_max_len < 2)
 
69
        return 0;
 
70
    va_start(args, fmt);
 
71
    n = vsnprintf(cp, cp_max_len, fmt, args);
 
72
    va_end(args);
 
73
    return (n < cp_max_len) ? n : (cp_max_len - 1);
 
74
}
 
75
 
51
76
/* Searches 'arr' for match on 'value' then 'peri_type'. If matches
52
77
   'value' but not 'peri_type' then yields first 'value' match entry.
53
78
   Last element of 'arr' has NULL 'name'. If no match returns NULL. */
108
133
{
109
134
    const char * ccp;
110
135
 
 
136
    if ((NULL == buff) || (buff_len < 1))
 
137
        return;
 
138
    else if (1 ==  buff_len) {
 
139
        buff[0] = '\0';
 
140
        return;
 
141
    }
111
142
    scsi_status &= 0x7e; /* sanitize as much as possible */
112
143
    switch (scsi_status) {
113
144
        case 0: ccp = "Good"; break;
123
154
        case 0x40: ccp = "Task Aborted"; break;
124
155
        default: ccp = "Unknown status"; break;
125
156
    }
126
 
    strncpy(buff, ccp, buff_len);
 
157
    my_snprintf(buff, buff_len, "%s", ccp);
127
158
}
128
159
 
129
160
void
142
173
char *
143
174
sg_get_sense_key_str(int sense_key, int buff_len, char * buff)
144
175
{
 
176
    if (1 == buff_len) {
 
177
        buff[0] = '\0';
 
178
        return buff;
 
179
    }
145
180
    if ((sense_key >= 0) && (sense_key < 16))
146
 
         snprintf(buff, buff_len, "%s", sg_lib_sense_key_desc[sense_key]);
 
181
         my_snprintf(buff, buff_len, "%s", sg_lib_sense_key_desc[sense_key]);
147
182
    else
148
 
         snprintf(buff, buff_len, "invalid value: 0x%x", sense_key);
 
183
         my_snprintf(buff, buff_len, "invalid value: 0x%x", sense_key);
149
184
    return buff;
150
185
}
151
186
 
157
192
    struct sg_lib_asc_ascq_t * eip;
158
193
    struct sg_lib_asc_ascq_range_t * ei2p;
159
194
 
 
195
    if (1 == buff_len) {
 
196
        buff[0] = '\0';
 
197
        return buff;
 
198
    }
160
199
    for (k = 0; sg_lib_asc_ascq_range[k].text; ++k) {
161
200
        ei2p = &sg_lib_asc_ascq_range[k];
162
201
        if ((ei2p->asc == asc) &&
163
202
            (ascq >= ei2p->ascq_min)  &&
164
203
            (ascq <= ei2p->ascq_max)) {
165
204
            found = 1;
166
 
            num = snprintf(buff, buff_len, "Additional sense: ");
 
205
            num = my_snprintf(buff, buff_len, "Additional sense: ");
167
206
            rlen = buff_len - num;
168
 
            num += snprintf(buff + num, ((rlen > 0) ? rlen : 0),
169
 
                            ei2p->text, ascq);
 
207
            num += my_snprintf(buff + num, ((rlen > 0) ? rlen : 0),
 
208
                               ei2p->text, ascq);
170
209
        }
171
210
    }
172
211
    if (found)
177
216
        if (eip->asc == asc &&
178
217
            eip->ascq == ascq) {
179
218
            found = 1;
180
 
            snprintf(buff, buff_len, "Additional sense: %s", eip->text);
 
219
            my_snprintf(buff, buff_len, "Additional sense: %s", eip->text);
181
220
        }
182
221
    }
183
222
    if (! found) {
184
223
        if (asc >= 0x80)
185
 
            snprintf(buff, buff_len, "vendor specific ASC=%2x, ASCQ=%2x",
186
 
                     asc, ascq);
 
224
            my_snprintf(buff, buff_len, "vendor specific ASC=%02x, "
 
225
                        "ASCQ=%02x (hex)", asc, ascq);
187
226
        else if (ascq >= 0x80)
188
 
            snprintf(buff, buff_len, "ASC=%2x, vendor specific qualification "
189
 
                     "ASCQ=%2x", asc, ascq);
 
227
            my_snprintf(buff, buff_len, "ASC=%02x, vendor specific "
 
228
                        "qualification ASCQ=%02x (hex)", asc, ascq);
190
229
        else
191
 
            snprintf(buff, buff_len, "ASC=%2x, ASCQ=%2x", asc, ascq);
 
230
            my_snprintf(buff, buff_len, "ASC=%02x, ASCQ=%02x (hex)", asc,
 
231
                        ascq);
192
232
    }
193
233
    return buff;
194
234
}
197
237
sg_scsi_sense_desc_find(const unsigned char * sensep, int sense_len,
198
238
                        int desc_type)
199
239
{
200
 
    int add_sen_len, add_len, desc_len, k;
 
240
    int add_sb_len, add_d_len, desc_len, k;
201
241
    const unsigned char * descp;
202
242
 
203
 
    if ((sense_len < 8) || (0 == (add_sen_len = sensep[7])))
 
243
    if ((sense_len < 8) || (0 == (add_sb_len = sensep[7])))
204
244
        return NULL;
205
245
    if ((sensep[0] < 0x72) || (sensep[0] > 0x73))
206
246
        return NULL;
207
 
    add_sen_len = (add_sen_len < (sense_len - 8)) ?
208
 
                         add_sen_len : (sense_len - 8);
 
247
    add_sb_len = (add_sb_len < (sense_len - 8)) ?
 
248
                         add_sb_len : (sense_len - 8);
209
249
    descp = &sensep[8];
210
 
    for (desc_len = 0, k = 0; k < add_sen_len; k += desc_len) {
 
250
    for (desc_len = 0, k = 0; k < add_sb_len; k += desc_len) {
211
251
        descp += desc_len;
212
 
        add_len = (k < (add_sen_len - 1)) ? descp[1]: -1;
213
 
        desc_len = add_len + 2;
 
252
        add_d_len = (k < (add_sb_len - 1)) ? descp[1]: -1;
 
253
        desc_len = add_d_len + 2;
214
254
        if (descp[0] == desc_type)
215
255
            return descp;
216
 
        if (add_len < 0) /* short descriptor ?? */
 
256
        if (add_d_len < 0) /* short descriptor ?? */
217
257
            break;
218
258
    }
219
259
    return NULL;
303
343
/* Returns 1 if SKSV is set and sense key is NO_SENSE or NOT_READY. Also
304
344
 * returns 1 if progress indication sense data descriptor found. Places
305
345
 * progress field from sense data where progress_outp points. If progress
306
 
 * field is not available returns 0. Handles both fixed and descriptor
307
 
 * sense formats. N.B. App should multiply by 100 and divide by 65536
308
 
 * to get percentage completion from given value. */
 
346
 * field is not available returns 0 and *progress_outp is unaltered. Handles
 
347
 * both fixed and descriptor sense formats.
 
348
 * Hint: if 1 is returned *progress_outp may be multiplied by 100 then
 
349
 * divided by 65536 to get the percentage completion. */
309
350
int
310
351
sg_get_sense_progress_fld(const unsigned char * sensep, int sb_len,
311
352
                          int * progress_outp)
354
395
sg_get_pdt_str(int pdt, int buff_len, char * buff)
355
396
{
356
397
    if ((pdt < 0) || (pdt > 31))
357
 
        snprintf(buff, buff_len, "bad pdt");
 
398
        my_snprintf(buff, buff_len, "bad pdt");
358
399
    else
359
 
        snprintf(buff, buff_len, "%s", sg_lib_pdt_strs[pdt]);
 
400
        my_snprintf(buff, buff_len, "%s", sg_lib_pdt_strs[pdt]);
360
401
    return buff;
361
402
}
362
403
 
364
405
sg_get_trans_proto_str(int tpi, int buff_len, char * buff)
365
406
{
366
407
    if ((tpi < 0) || (tpi > 15))
367
 
        snprintf(buff, buff_len, "bad tpi");
 
408
        my_snprintf(buff, buff_len, "bad tpi");
368
409
    else
369
 
        snprintf(buff, buff_len, "%s", sg_lib_transport_proto_strs[tpi]);
 
410
        my_snprintf(buff, buff_len, "%s", sg_lib_transport_proto_strs[tpi]);
370
411
    return buff;
371
412
}
372
413
 
382
423
{
383
424
    switch (st) {
384
425
    case TPGS_STATE_OPTIMIZED:
385
 
        return snprintf(b, blen, "active/optimized");
 
426
        return my_snprintf(b, blen, "active/optimized");
386
427
    case TPGS_STATE_NONOPTIMIZED:
387
 
        return snprintf(b, blen, "active/non optimized");
 
428
        return my_snprintf(b, blen, "active/non optimized");
388
429
    case TPGS_STATE_STANDBY:
389
 
        return snprintf(b, blen, "standby");
 
430
        return my_snprintf(b, blen, "standby");
390
431
    case TPGS_STATE_UNAVAILABLE:
391
 
        return snprintf(b, blen, "unavailable");
 
432
        return my_snprintf(b, blen, "unavailable");
392
433
    case TPGS_STATE_OFFLINE:
393
 
        return snprintf(b, blen, "offline");
 
434
        return my_snprintf(b, blen, "offline");
394
435
    case TPGS_STATE_TRANSITIONING:
395
 
        return snprintf(b, blen, "transitioning between states");
 
436
        return my_snprintf(b, blen, "transitioning between states");
396
437
    default:
397
 
        return snprintf(b, blen, "unknown: 0x%x", st);
 
438
        return my_snprintf(b, blen, "unknown: 0x%x", st);
398
439
    }
399
440
}
400
441
 
401
442
static int
402
 
uds_referral_descriptor_str(char * sp, const unsigned char * dp, int alen)
 
443
uds_referral_descriptor_str(char * b, int blen, const unsigned char * dp,
 
444
                            int alen)
403
445
{
404
446
    int n = 0;
405
447
    int dlen = alen - 2;
408
450
    uint64_t ull;
409
451
    char c[40];
410
452
 
411
 
    n += sprintf(sp + n, "   Not all referrals: %d\n", !!(dp[2] & 0x1));
 
453
    n += my_snprintf(b + n, blen - n, "   Not all referrals: %d\n",
 
454
                     !!(dp[2] & 0x1));
412
455
    dp += 4;
413
456
    for (k = 0, f = 1; (k + 4) < dlen; k += g, dp += g, ++f) {
414
457
        tpgd = dp[3];
415
458
        g = (tpgd * 4) + 20;
416
 
        n += sprintf(sp + n, "    Descriptor %d\n", f);
 
459
        n += my_snprintf(b + n, blen - n, "    Descriptor %d\n", f);
417
460
        if ((k + g) > dlen) {
418
 
            n += sprintf(sp + n, "      truncated descriptor, stop\n");
 
461
            n += my_snprintf(b + n, blen - n, "      truncated descriptor, "
 
462
                             "stop\n");
419
463
            return n;
420
464
        }
421
465
        ull = 0;
424
468
                ull <<= 8;
425
469
            ull |= dp[4 + j];
426
470
        }
427
 
        n += sprintf(sp + n, "      first uds LBA: 0x%"PRIx64"\n", ull);
 
471
        n += my_snprintf(b + n, blen - n, "      first uds LBA: 0x%"PRIx64
 
472
                         "\n", ull);
428
473
        ull = 0;
429
474
        for (j = 0; j < 8; ++j) {
430
475
            if (j > 0)
431
476
                ull <<= 8;
432
477
            ull |= dp[12 + j];
433
478
        }
434
 
        n += sprintf(sp + n, "      last uds LBA:  0x%"PRIx64"\n", ull);
 
479
        n += my_snprintf(b + n, blen - n, "      last uds LBA:  0x%"PRIx64
 
480
                         "\n", ull);
435
481
        for (j = 0; j < tpgd; ++j) {
436
482
            tp = dp + 20 + (j * 4);
437
483
            decode_tpgs_state(tp[0] & 0xf, c, sizeof(c));
438
 
            n += sprintf(sp + n, "        tpg: %d  state: %s\n",
439
 
                         (tp[2] << 8) + tp[3], c);
 
484
            n += my_snprintf(b + n, blen - n, "        tpg: %d  state: %s\n",
 
485
                             (tp[2] << 8) + tp[3], c);
440
486
        }
441
487
    }
442
488
    return n;
449
495
    };
450
496
 
451
497
 
452
 
/* Print descriptor format sense descriptors (assumes sense buffer is
 
498
/* Decode descriptor format sense descriptors (assumes sense buffer is
453
499
   in descriptor format) */
454
500
static void
455
501
sg_get_sense_descriptors_str(const unsigned char * sense_buffer, int sb_len,
456
 
                             int buff_len, char * buff)
 
502
                             int blen, char * b)
457
503
{
458
 
    int add_sen_len, add_len, desc_len, k, j, sense_key, processed;
 
504
    int add_sb_len, add_d_len, desc_len, k, j, sense_key, processed;
459
505
    int n, progress, pr, rem;
460
506
    const unsigned char * descp;
461
507
    const char * dtsp = "   >> descriptor too short";
462
 
    char b[2048];
463
508
 
464
 
    if ((NULL == buff) || (buff_len <= 0))
465
 
        return;
466
 
    buff[0] = '\0';
467
 
    if ((sb_len < 8) || (0 == (add_sen_len = sense_buffer[7])))
468
 
        return;
469
 
    add_sen_len = (add_sen_len < (sb_len - 8)) ? add_sen_len : (sb_len - 8);
470
 
    descp = &sense_buffer[8];
 
509
    if ((NULL == b) || (blen <= 0))
 
510
        return;
 
511
    b[0] = '\0';
 
512
    if ((sb_len < 8) || (0 == (add_sb_len = sense_buffer[7])))
 
513
        return;
 
514
    add_sb_len = (add_sb_len < (sb_len - 8)) ? add_sb_len : (sb_len - 8);
471
515
    sense_key = (sense_buffer[1] & 0xf);
472
 
    for (desc_len = 0, k = 0; k < add_sen_len; k += desc_len) {
473
 
        descp += desc_len;
474
 
        add_len = (k < (add_sen_len - 1)) ? descp[1] : -1;
475
 
        if ((k + add_len + 2) > add_sen_len)
476
 
            add_len = add_sen_len - k - 2;
477
 
        desc_len = add_len + 2;
478
 
        n = 0;
479
 
        n += sprintf(b + n, "  Descriptor type: ");
 
516
 
 
517
    for (descp = (sense_buffer + 8), k = 0, n = 0;
 
518
         (k < add_sb_len) && (n < blen);
 
519
         k += desc_len, descp += desc_len) {
 
520
        add_d_len = (k < (add_sb_len - 1)) ? descp[1] : -1;
 
521
        if ((k + add_d_len + 2) > add_sb_len)
 
522
            add_d_len = add_sb_len - k - 2;
 
523
        desc_len = add_d_len + 2;
 
524
        n += my_snprintf(b + n, blen - n, "  Descriptor type: ");
480
525
        processed = 1;
481
526
        switch (descp[0]) {
482
527
        case 0:
483
 
            n += sprintf(b + n, "Information\n");
484
 
            if ((add_len >= 10) && (0x80 & descp[2])) {
485
 
                n += sprintf(b + n, "    0x");
 
528
            n += my_snprintf(b + n, blen - n, "Information\n");
 
529
            if ((add_d_len >= 10) && (0x80 & descp[2])) {
 
530
                n += my_snprintf(b + n, blen - n, "    0x");
486
531
                for (j = 0; j < 8; ++j)
487
 
                    n += sprintf(b + n, "%02x", descp[4 + j]);
488
 
                n += sprintf(b + n, "\n");
 
532
                    n += my_snprintf(b + n, blen - n, "%02x", descp[4 + j]);
 
533
                n += my_snprintf(b + n, blen - n, "\n");
489
534
            } else {
490
 
                n += sprintf(b + n, "%s\n", dtsp);
 
535
                n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
491
536
                processed = 0;
492
537
            }
493
538
            break;
494
539
        case 1:
495
 
            n += sprintf(b + n, "Command specific\n");
496
 
            if (add_len >= 10) {
497
 
                n += sprintf(b + n, "    0x");
 
540
            n += my_snprintf(b + n, blen - n, "Command specific\n");
 
541
            if (add_d_len >= 10) {
 
542
                n += my_snprintf(b + n, blen - n, "    0x");
498
543
                for (j = 0; j < 8; ++j)
499
 
                    n += sprintf(b + n, "%02x", descp[4 + j]);
500
 
                n += sprintf(b + n, "\n");
 
544
                    n += my_snprintf(b + n, blen - n, "%02x", descp[4 + j]);
 
545
                n += my_snprintf(b + n, blen - n, "\n");
501
546
            } else {
502
 
                n += sprintf(b + n, "%s\n", dtsp);
 
547
                n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
503
548
                processed = 0;
504
549
            }
505
550
            break;
506
551
        case 2:
507
 
            n += sprintf(b + n, "Sense key specific:");
 
552
            n += my_snprintf(b + n, blen - n, "Sense key specific:");
508
553
            switch (sense_key) {
509
554
            case SPC_SK_ILLEGAL_REQUEST:
510
 
                n += sprintf(b + n, " Field pointer\n");
511
 
                if (add_len < 6) {
512
 
                    n += sprintf(b + n, "%s\n", dtsp);
 
555
                n += my_snprintf(b + n, blen - n, " Field pointer\n");
 
556
                if (add_d_len < 6) {
 
557
                    n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
513
558
                    processed = 0;
514
559
                    break;
515
560
                }
516
 
                n += sprintf(b + n, "    Error in %s byte %d",
517
 
                        (descp[4] & 0x40) ? "Command" : "Data",
518
 
                        (descp[5] << 8) | descp[6]);
 
561
                n += my_snprintf(b + n, blen - n, "    Error in %s byte %d",
 
562
                                 (descp[4] & 0x40) ? "Command" : "Data",
 
563
                                 (descp[5] << 8) | descp[6]);
519
564
                if (descp[4] & 0x08) {
520
 
                    n += sprintf(b + n, " bit %d\n", descp[4] & 0x07);
 
565
                    n += my_snprintf(b + n, blen - n, " bit %d\n",
 
566
                                     descp[4] & 0x07);
521
567
                } else
522
 
                    n += sprintf(b + n, "\n");
 
568
                    n += my_snprintf(b + n, blen - n, "\n");
523
569
                break;
524
570
            case SPC_SK_HARDWARE_ERROR:
525
571
            case SPC_SK_MEDIUM_ERROR:
526
572
            case SPC_SK_RECOVERED_ERROR:
527
 
                n += sprintf(b + n, " Actual retry count\n");
528
 
                if (add_len < 6) {
529
 
                    n += sprintf(b + n, "%s\n", dtsp);
 
573
                n += my_snprintf(b + n, blen - n, " Actual retry count\n");
 
574
                if (add_d_len < 6) {
 
575
                    n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
530
576
                    processed = 0;
531
577
                    break;
532
578
                }
533
 
                n += sprintf(b + n, "    0x%02x%02x\n", descp[5],
534
 
                        descp[6]);
 
579
                n += my_snprintf(b + n, blen - n,"    0x%02x%02x\n", descp[5],
 
580
                                 descp[6]);
535
581
                break;
536
582
            case SPC_SK_NO_SENSE:
537
583
            case SPC_SK_NOT_READY:
538
 
                n += sprintf(b + n, " Progress indication: ");
539
 
                if (add_len < 6) {
540
 
                    n += sprintf(b + n, "%s\n", dtsp);
 
584
                n += my_snprintf(b + n, blen - n, " Progress indication: ");
 
585
                if (add_d_len < 6) {
 
586
                    n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
541
587
                    processed = 0;
542
588
                    break;
543
589
                }
544
590
                progress = (descp[5] << 8) + descp[6];
545
591
                pr = (progress * 100) / 65536;
546
 
                rem = ((progress * 100) % 65536) / 655;
547
 
                n += sprintf(b + n, "%d.%02d%%\n", pr, rem);
 
592
                rem = ((progress * 100) % 65536) / 656;
 
593
                n += my_snprintf(b + n, blen - n, "%d.%02d%%\n", pr, rem);
548
594
                break;
549
595
            case SPC_SK_COPY_ABORTED:
550
 
                n += sprintf(b + n, " Segment pointer\n");
551
 
                if (add_len < 6) {
552
 
                    n += sprintf(b + n, "%s\n", dtsp);
 
596
                n += my_snprintf(b + n, blen - n, " Segment pointer\n");
 
597
                if (add_d_len < 6) {
 
598
                    n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
553
599
                    processed = 0;
554
600
                    break;
555
601
                }
556
 
                n += sprintf(b + n, " Relative to start of %s, byte %d",
557
 
                        (descp[4] & 0x20) ? "segment descriptor" :
558
 
                                            "parameter list",
559
 
                        (descp[5] << 8) | descp[6]);
 
602
                n += my_snprintf(b + n, blen - n, " Relative to start of %s, "
 
603
                                 "byte %d",
 
604
                                 (descp[4] & 0x20) ? "segment descriptor" :
 
605
                                                     "parameter list",
 
606
                                 (descp[5] << 8) | descp[6]);
560
607
                if (descp[4] & 0x08)
561
 
                    n += sprintf(b + n, " bit %d\n", descp[4] & 0x07);
 
608
                    n += my_snprintf(b + n, blen - n, " bit %d\n",
 
609
                                     descp[4] & 0x07);
562
610
                else
563
 
                    n += sprintf(b + n, "\n");
 
611
                    n += my_snprintf(b + n, blen - n, "\n");
564
612
                break;
565
613
            case SPC_SK_UNIT_ATTENTION:
566
 
                n += sprintf(b + n, " Unit attention condition queue: ");
567
 
                n += sprintf(b + n, "overflow flag is %d\n",
 
614
                n += my_snprintf(b + n, blen - n, " Unit attention condition "
 
615
                                 "queue: ");
 
616
                n += my_snprintf(b + n, blen - n, "overflow flag is %d\n",
568
617
                             !!(descp[4] & 0x1));
569
618
                break;
570
619
            default:
571
 
                n += sprintf(b + n, " Sense_key: 0x%x unexpected\n",
572
 
                        sense_key);
 
620
                n += my_snprintf(b + n, blen - n, " Sense_key: 0x%x "
 
621
                                 "unexpected\n", sense_key);
573
622
                processed = 0;
574
623
                break;
575
624
            }
576
625
            break;
577
626
        case 3:
578
 
            n += sprintf(b + n, "Field replaceable unit\n");
579
 
            if (add_len >= 2)
580
 
                n += sprintf(b + n, "    code=0x%x\n", descp[3]);
 
627
            n += my_snprintf(b + n, blen - n, "Field replaceable unit\n");
 
628
            if (add_d_len >= 2)
 
629
                n += my_snprintf(b + n, blen - n, "    code=0x%x\n",
 
630
                                 descp[3]);
581
631
            else {
582
 
                n += sprintf(b + n, "%s\n", dtsp);
 
632
                n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
583
633
                processed = 0;
584
634
            }
585
635
            break;
586
636
        case 4:
587
 
            n += sprintf(b + n, "Stream commands\n");
588
 
            if (add_len >= 2) {
 
637
            n += my_snprintf(b + n, blen - n, "Stream commands\n");
 
638
            if (add_d_len >= 2) {
589
639
                if (descp[3] & 0x80)
590
 
                    n += sprintf(b + n, "    FILEMARK");
 
640
                    n += my_snprintf(b + n, blen - n, "    FILEMARK");
591
641
                if (descp[3] & 0x40)
592
 
                    n += sprintf(b + n, "    End Of Medium (EOM)");
 
642
                    n += my_snprintf(b + n, blen - n, "    End Of Medium "
 
643
                                     "(EOM)");
593
644
                if (descp[3] & 0x20)
594
 
                    n += sprintf(b + n, "    Incorrect Length Indicator "
595
 
                            "(ILI)");
596
 
                n += sprintf(b + n, "\n");
 
645
                    n += my_snprintf(b + n, blen - n, "    Incorrect Length "
 
646
                                     "Indicator (ILI)");
 
647
                n += my_snprintf(b + n, blen - n, "\n");
597
648
            } else {
598
 
                n += sprintf(b + n, "%s\n", dtsp);
 
649
                n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
599
650
                processed = 0;
600
651
            }
601
652
            break;
602
653
        case 5:
603
 
            n += sprintf(b + n, "Block commands\n");
604
 
            if (add_len >= 2)
605
 
                n += sprintf(b + n, "    Incorrect Length Indicator "
606
 
                        "(ILI) %s\n", (descp[3] & 0x20) ? "set" : "clear");
 
654
            n += my_snprintf(b + n, blen - n, "Block commands\n");
 
655
            if (add_d_len >= 2)
 
656
                n += my_snprintf(b + n, blen - n, "    Incorrect Length "
 
657
                                 "Indicator (ILI) %s\n",
 
658
                                 (descp[3] & 0x20) ? "set" : "clear");
607
659
            else {
608
 
                n += sprintf(b + n, "%s\n", dtsp);
 
660
                n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
609
661
                processed = 0;
610
662
            }
611
663
            break;
612
664
        case 6:
613
 
            n += sprintf(b + n, "OSD object identification\n");
 
665
            n += my_snprintf(b + n, blen - n, "OSD object identification\n");
614
666
            processed = 0;
615
667
            break;
616
668
        case 7:
617
 
            n += sprintf(b + n, "OSD response integrity check value\n");
 
669
            n += my_snprintf(b + n, blen - n, "OSD response integrity check "
 
670
                             "value\n");
618
671
            processed = 0;
619
672
            break;
620
673
        case 8:
621
 
            n += sprintf(b + n, "OSD attribute identification\n");
 
674
            n += my_snprintf(b + n, blen - n, "OSD attribute "
 
675
                             "identification\n");
622
676
            processed = 0;
623
677
            break;
624
 
        case 9:
625
 
            n += sprintf(b + n, "ATA Status Return\n");
626
 
            if (add_len >= 12) {
 
678
        case 9:         /* this is defined in SAT (and SAT-2) */
 
679
            n += my_snprintf(b + n, blen - n, "ATA Status Return\n");
 
680
            if (add_d_len >= 12) {
627
681
                int extend, sector_count;
628
682
 
629
683
                extend = descp[2] & 1;
630
684
                sector_count = descp[5] + (extend ? (descp[4] << 8) : 0);
631
 
                n += sprintf(b + n, "    extend=%d  error=0x%x "
632
 
                        " sector_count=0x%x\n", extend, descp[3],
633
 
                        sector_count);
 
685
                n += my_snprintf(b + n, blen - n, "    extend=%d  error=0x%x "
 
686
                                 " sector_count=0x%x\n", extend, descp[3],
 
687
                                 sector_count);
634
688
                if (extend)
635
 
                    n += sprintf(b + n, "    lba=0x%02x%02x%02x%02x%02x%02x\n",
636
 
                                 descp[10], descp[8], descp[6],
637
 
                                 descp[11], descp[9], descp[7]);
 
689
                    n += my_snprintf(b + n, blen - n, "    "
 
690
                                     "lba=0x%02x%02x%02x%02x%02x%02x\n",
 
691
                                     descp[10], descp[8], descp[6],
 
692
                                     descp[11], descp[9], descp[7]);
638
693
                else
639
 
                    n += sprintf(b + n, "    lba=0x%02x%02x%02x\n",
640
 
                                 descp[11], descp[9], descp[7]);
641
 
                n += sprintf(b + n, "    device=0x%x  status=0x%x\n",
642
 
                        descp[12], descp[13]);
 
694
                    n += my_snprintf(b + n, blen - n, "    "
 
695
                                     "lba=0x%02x%02x%02x\n",
 
696
                                     descp[11], descp[9], descp[7]);
 
697
                n += my_snprintf(b + n, blen - n, "    device=0x%x  "
 
698
                                 "status=0x%x\n", descp[12], descp[13]);
643
699
            } else {
644
 
                n += sprintf(b + n, "%s\n", dtsp);
 
700
                n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
645
701
                processed = 0;
646
702
            }
647
703
            break;
648
 
        case 0xa:       /* Added in SPC-4 rev 17 */
649
 
            n += sprintf(b + n, "Progress indication\n");
650
 
            if (add_len < 6) {
651
 
                n += sprintf(b + n, "%s\n", dtsp);
 
704
        case 0xa:
 
705
           /* Added in SPC-4 rev 17, became 'Another ...' in rev 34 */
 
706
            n += my_snprintf(b + n, blen - n, "Another progress "
 
707
                             "indication\n");
 
708
            if (add_d_len < 6) {
 
709
                n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
652
710
                processed = 0;
653
711
                break;
654
712
            }
655
713
            progress = (descp[6] << 8) + descp[7];
656
714
            pr = (progress * 100) / 65536;
657
 
            rem = ((progress * 100) % 65536) / 655;
658
 
            n += sprintf(b + n, "    %d.02%d%%", pr, rem);
659
 
            n += sprintf(b + n, " [sense_key=0x%x asc,ascq=0x%x,0x%x]\n",
660
 
                         descp[2], descp[3], descp[4]);
 
715
            rem = ((progress * 100) % 65536) / 656;
 
716
            n += my_snprintf(b + n, blen - n, "    %d.02%d%%", pr, rem);
 
717
            n += my_snprintf(b + n, blen - n, " [sense_key=0x%x "
 
718
                             "asc,ascq=0x%x,0x%x]\n",
 
719
                             descp[2], descp[3], descp[4]);
661
720
            break;
662
721
        case 0xb:       /* Added in SPC-4 rev 23, defined in SBC-3 rev 22 */
663
 
            n += sprintf(b + n, "User data segment referral\n");
664
 
            if (add_len < 2) {
665
 
                n += sprintf(b + n, "%s\n", dtsp);
 
722
            n += my_snprintf(b + n, blen - n, "User data segment referral\n");
 
723
            if (add_d_len < 2) {
 
724
                n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
666
725
                processed = 0;
667
726
                break;
668
727
            }
669
 
            n += uds_referral_descriptor_str(b + n, descp, add_len);
 
728
            n += uds_referral_descriptor_str(b + n, blen - n, descp,
 
729
                                             add_d_len);
670
730
            break;
671
731
        case 0xc:       /* Added in SPC-4 rev 28 */
672
 
            n += sprintf(b + n, "Forwarded sense data\n");
673
 
            if (add_len < 2) {
674
 
                n += sprintf(b + n, "%s\n", dtsp);
 
732
            n += my_snprintf(b + n, blen - n, "Forwarded sense data\n");
 
733
            if (add_d_len < 2) {
 
734
                n += my_snprintf(b + n, blen - n, "%s\n", dtsp);
675
735
                processed = 0;
676
736
                break;
677
737
            }
678
 
            n += sprintf(b + n, "    FSDT: %s\n",
679
 
                         (descp[2] & 0x80) ? "set" : "clear");
 
738
            n += my_snprintf(b + n, blen - n, "    FSDT: %s\n",
 
739
                             (descp[2] & 0x80) ? "set" : "clear");
680
740
            j = descp[2] & 0xf;
681
741
            if (j < 3)
682
 
                n += sprintf(b + n, "    Sense data source: %s\n",
683
 
                             sdata_src[j]);
 
742
                n += my_snprintf(b + n, blen - n, "    Sense data source: "
 
743
                                 "%s\n", sdata_src[j]);
684
744
            else
685
 
                n += sprintf(b + n, "    Sense data source: reserved [%d]\n",
686
 
                             j);
 
745
                n += my_snprintf(b + n, blen - n, "    Sense data source: "
 
746
                                 "reserved [%d]\n", j);
687
747
            {
688
748
                char c[200];
689
749
 
690
750
                sg_get_scsi_status_str(descp[3], sizeof(c) - 1, c);
691
751
                c[sizeof(c) - 1] = '\0';
692
 
                n += sprintf(b + n, "    Forwarded status: %s\n", c);
693
 
                if (add_len > 2) {
 
752
                n += my_snprintf(b + n, blen - n, "    Forwarded status: "
 
753
                                 "%s\n", c);
 
754
                if (add_d_len > 2) {
694
755
                    /* recursing; hope not to get carried away */
695
 
                    n += sprintf(b + n, " vvvvvvvvvvvvvvvv\n");
696
 
                    sg_get_sense_str(NULL, descp + 4, add_len - 2, 0,
 
756
                    n += my_snprintf(b + n, blen - n, " vvvvvvvvvvvvvvvv\n");
 
757
                    sg_get_sense_str(NULL, descp + 4, add_d_len - 2, 0,
697
758
                                     sizeof(c), c);
698
 
                    n += sprintf(b + n, "%s", c);
699
 
                    n += sprintf(b + n, " ^^^^^^^^^^^^^^^^\n");
 
759
                    n += my_snprintf(b + n, blen - n, "%s", c);
 
760
                    n += my_snprintf(b + n, blen - n, " ^^^^^^^^^^^^^^^^\n");
700
761
                }
701
762
            }
702
763
            break;
703
764
        default:
704
765
            if (descp[0] >= 0x80)
705
 
                n += sprintf(b + n, "Vendor specific [0x%x]\n", descp[0]);
 
766
                n += my_snprintf(b + n, blen - n, "Vendor specific [0x%x]\n",
 
767
                                 descp[0]);
706
768
            else
707
 
                n += sprintf(b + n, "Unknown [0x%x]\n", descp[0]);
 
769
                n += my_snprintf(b + n, blen - n, "Unknown [0x%x]\n",
 
770
                                 descp[0]);
708
771
            processed = 0;
709
772
            break;
710
773
        }
711
774
        if (! processed) {
712
 
            if (add_len > 0) {
713
 
                n += sprintf(b + n, "    ");
714
 
                for (j = 0; j < add_len; ++j) {
 
775
            if (add_d_len > 0) {
 
776
                n += my_snprintf(b + n, blen - n, "    ");
 
777
                for (j = 0; j < add_d_len; ++j) {
715
778
                    if ((j > 0) && (0 == (j % 24)))
716
 
                        n += sprintf(b + n, "\n    ");
717
 
                    n += sprintf(b + n, "%02x ", descp[j + 2]);
 
779
                        n += my_snprintf(b + n, blen - n, "\n    ");
 
780
                    n += my_snprintf(b + n, blen - n, "%02x ", descp[j + 2]);
718
781
                }
719
 
                n += sprintf(b + n, "\n");
 
782
                n += my_snprintf(b + n, blen - n, "\n");
720
783
            }
721
784
        }
722
 
        if (add_len < 0)
723
 
            n += sprintf(b + n, "    short descriptor\n");
724
 
        j = strlen(buff);
725
 
        if ((n + j) >= buff_len) {
726
 
            strncpy(buff + j, b, buff_len - j);
727
 
            buff[buff_len - 1] = '\0';
728
 
            break;
729
 
        }
730
 
        strcpy(buff + j, b);
731
 
        if (add_len < 0)
732
 
            break;
 
785
        if (add_d_len < 0)
 
786
            n += my_snprintf(b + n, blen - n, "    short descriptor\n");
733
787
    }
734
788
}
735
789
 
 
790
/* Decode SAT ATA PASS-THROUGH fixed format sense */
 
791
static void
 
792
sg_get_sense_sat_pt_fixed_str(const unsigned char * sp, int slen, int blen,
 
793
                              char * b)
 
794
{
 
795
    int n = 0;
 
796
 
 
797
    slen = slen;        /* suppress warning */
 
798
    if (blen < 1)
 
799
        return;
 
800
    if (SPC_SK_RECOVERED_ERROR != (0xf & sp[2]))
 
801
        n += my_snprintf(b + n, blen - n, "  >> expected Sense key: "
 
802
                         "Recovered Error ??\n");
 
803
    n += my_snprintf(b + n, blen - n, "  error=0x%x, status=0x%x, "
 
804
                     "device=0x%x, sector_count(7:0)=0x%x%c\n", sp[3], sp[4],
 
805
                     sp[5], sp[6], ((0x40 & sp[8]) ? '+' : ' '));
 
806
    n += my_snprintf(b + n, blen - n, "  extend=%d, log_index=0x%x, "
 
807
                     "lba_high,mid,low(7:0)=0x%x,0x%x,0x%x%c\n",
 
808
                     (!!(0x80 & sp[8])), (0xf & sp[8]), sp[9], sp[10], sp[11],
 
809
                     ((0x20 & sp[8]) ? '+' : ' '));
 
810
}
 
811
 
736
812
/* Fetch sense information */
737
813
void
738
814
sg_get_sense_str(const char * leadin, const unsigned char * sense_buffer,
739
815
                 int sb_len, int raw_sinfo, int buff_len, char * buff)
740
816
{
741
 
    int len, valid, progress, n, r, pr, rem;
 
817
    int len, valid, progress, n, r, pr, rem, blen;
742
818
    unsigned int info;
743
819
    int descriptor_format = 0;
744
 
    const char * error = NULL;
 
820
    int sdat_ovfl = 0;
 
821
    const char * ebp = NULL;
745
822
    char error_buff[64];
746
823
    char b[256];
747
824
    struct sg_scsi_sense_hdr ssh;
748
825
 
749
826
    if ((NULL == buff) || (buff_len <= 0))
750
827
        return;
751
 
    buff[buff_len - 1] = '\0';
752
 
    --buff_len;
 
828
    else if (1 == buff_len) {
 
829
        buff[0] = '\0';
 
830
        return;
 
831
    }
 
832
    blen = sizeof(b);
753
833
    n = 0;
754
834
    if (sb_len < 1) {
755
 
            snprintf(buff, buff_len, "sense buffer empty\n");
756
 
            return;
757
 
    }
758
 
    if (leadin) {
759
 
        n += snprintf(buff + n, buff_len - n, "%s: ", leadin);
760
 
        if (n >= buff_len)
761
 
            return;
762
 
    }
 
835
            my_snprintf(buff, buff_len, "sense buffer empty\n");
 
836
            return;
 
837
    }
 
838
    if (leadin)
 
839
        n += my_snprintf(buff + n, buff_len - n, "%s: ", leadin);
763
840
    len = sb_len;
764
841
    if (sg_scsi_normalize_sense(sense_buffer, sb_len, &ssh)) {
765
842
        switch (ssh.response_code) {
766
843
        case 0x70:      /* fixed, current */
767
 
            error = "Fixed format, current";
 
844
            ebp = "Fixed format, current";
768
845
            len = (sb_len > 7) ? (sense_buffer[7] + 8) : sb_len;
769
846
            len = (len > sb_len) ? sb_len : len;
 
847
            sdat_ovfl = (len > 2) ? !!(sense_buffer[2] & 0x10) : 0;
770
848
            break;
771
849
        case 0x71:      /* fixed, deferred */
772
850
            /* error related to a previous command */
773
 
            error = "Fixed format, <<<deferred>>>";
 
851
            ebp = "Fixed format, <<<deferred>>>";
774
852
            len = (sb_len > 7) ? (sense_buffer[7] + 8) : sb_len;
775
853
            len = (len > sb_len) ? sb_len : len;
 
854
            sdat_ovfl = (len > 2) ? !!(sense_buffer[2] & 0x10) : 0;
776
855
            break;
777
856
        case 0x72:      /* descriptor, current */
778
857
            descriptor_format = 1;
779
 
            error = "Descriptor format, current";
 
858
            ebp = "Descriptor format, current";
 
859
            sdat_ovfl = (sb_len > 4) ? !!(sense_buffer[4] & 0x80) : 0;
780
860
            break;
781
861
        case 0x73:      /* descriptor, deferred */
782
862
            descriptor_format = 1;
783
 
            error = "Descriptor format, <<<deferred>>>";
 
863
            ebp = "Descriptor format, <<<deferred>>>";
 
864
            sdat_ovfl = (sb_len > 4) ? !!(sense_buffer[4] & 0x80) : 0;
784
865
            break;
785
866
        case 0x0:
786
 
            error = "Response code: 0x0 (?)";
 
867
            ebp = "Response code: 0x0 (?)";
787
868
            break;
788
869
        default:
789
 
            snprintf(error_buff, sizeof(error_buff),
790
 
                     "Unknown response code: 0x%x", ssh.response_code);
791
 
            error = error_buff;
 
870
            my_snprintf(error_buff, sizeof(error_buff),
 
871
                        "Unknown response code: 0x%x", ssh.response_code);
 
872
            ebp = error_buff;
792
873
            break;
793
874
        }
794
 
        n += snprintf(buff + n, buff_len - n, " %s;  Sense key: %s\n ",
795
 
                      error, sg_lib_sense_key_desc[ssh.sense_key]);
796
 
        if (n >= buff_len)
797
 
            return;
 
875
        n += my_snprintf(buff + n, buff_len - n, " %s;  Sense key: %s\n ",
 
876
                         ebp, sg_lib_sense_key_desc[ssh.sense_key]);
 
877
        if (sdat_ovfl)
 
878
            n += my_snprintf(buff + n, buff_len - n, "<<<Sense data "
 
879
                             "overflow>>>\n");
798
880
        if (descriptor_format) {
799
 
            n += snprintf(buff + n, buff_len - n, "%s\n",
800
 
                          sg_get_asc_ascq_str(ssh.asc, ssh.ascq,
801
 
                                              sizeof(b), b));
802
 
            if (n >= buff_len)
803
 
                return;
 
881
            n += my_snprintf(buff + n, buff_len - n, "%s\n",
 
882
                             sg_get_asc_ascq_str(ssh.asc, ssh.ascq,
 
883
                                                 sizeof(b), b));
804
884
            sg_get_sense_descriptors_str(sense_buffer, len, buff_len - n,
805
885
                                         buff + n);
806
886
            n = strlen(buff);
807
 
            if (n >= buff_len)
808
 
                return;
 
887
        } else if ((len > 12) && (0 == ssh.asc) &&
 
888
                   (ASCQ_ATA_PT_INFO_AVAILABLE == ssh.ascq)) {
 
889
            /* SAT ATA PASS-THROUGH fixed format */
 
890
            n += my_snprintf(buff + n, buff_len - n, "%s\n",
 
891
                             sg_get_asc_ascq_str(ssh.asc, ssh.ascq,
 
892
                             sizeof(b), b));
 
893
            sg_get_sense_sat_pt_fixed_str(sense_buffer, len, buff_len - n,
 
894
                                          buff + n);
 
895
            n = strlen(buff);
809
896
        } else if (len > 2) {   /* fixed format */
810
 
            if (len > 12) {
811
 
                n += snprintf(buff + n, buff_len - n, "%s\n",
812
 
                              sg_get_asc_ascq_str(ssh.asc, ssh.ascq,
813
 
                                                  sizeof(b), b));
814
 
                if (n >= buff_len)
815
 
                    return;
816
 
            }
 
897
            if (len > 12)
 
898
                n += my_snprintf(buff + n, buff_len - n, "%s\n",
 
899
                                 sg_get_asc_ascq_str(ssh.asc, ssh.ascq,
 
900
                                                     sizeof(b), b));
817
901
            r = 0;
818
902
            valid = sense_buffer[0] & 0x80;
819
903
            if (len > 6) {
821
905
                        (sense_buffer[4] << 16) | (sense_buffer[5] << 8) |
822
906
                        sense_buffer[6]);
823
907
                if (valid)
824
 
                    r += sprintf(b + r, "  Info fld=0x%x [%u] ", info,
825
 
                                 info);
 
908
                    r += my_snprintf(b + r, blen - r, "  Info fld=0x%x [%u] ",
 
909
                                     info, info);
826
910
                else if (info > 0)
827
 
                    r += sprintf(b + r, "  Valid=0, Info fld=0x%x [%u] ",
828
 
                                 info, info);
 
911
                    r += my_snprintf(b + r, blen - r, "  Valid=0, Info "
 
912
                                     "fld=0x%x [%u] ", info, info);
829
913
            } else
830
914
                info = 0;
831
915
            if (sense_buffer[2] & 0xe0) {
832
916
                if (sense_buffer[2] & 0x80)
833
 
                   r += sprintf(b + r, " FMK");
 
917
                   r += my_snprintf(b + r, blen - r, " FMK");
834
918
                            /* current command has read a filemark */
835
919
                if (sense_buffer[2] & 0x40)
836
 
                   r += sprintf(b + r, " EOM");
 
920
                   r += my_snprintf(b + r, blen - r, " EOM");
837
921
                            /* end-of-medium condition exists */
838
922
                if (sense_buffer[2] & 0x20)
839
 
                   r += sprintf(b + r, " ILI");
 
923
                   r += my_snprintf(b + r, blen - r, " ILI");
840
924
                            /* incorrect block length requested */
841
 
                r += sprintf(b + r, "\n");
 
925
                r += my_snprintf(b + r, blen - r, "\n");
842
926
            } else if (valid || (info > 0))
843
 
                r += sprintf(b + r, "\n");
 
927
                r += my_snprintf(b + r, blen - r, "\n");
844
928
            if ((len >= 14) && sense_buffer[14])
845
 
                r += sprintf(b + r, "  Field replaceable unit code: "
846
 
                             "%d\n", sense_buffer[14]);
 
929
                r += my_snprintf(b + r, blen - r, "  Field replaceable unit "
 
930
                                 "code: %d\n", sense_buffer[14]);
847
931
            if ((len >= 18) && (sense_buffer[15] & 0x80)) {
848
932
                /* sense key specific decoding */
849
933
                switch (ssh.sense_key) {
850
934
                case SPC_SK_ILLEGAL_REQUEST:
851
 
                    r += sprintf(b + r, "  Sense Key Specific: Error in "
852
 
                                 "%s byte %d", (sense_buffer[15] & 0x40) ?
853
 
                                                 "Command" : "Data",
854
 
                                 (sense_buffer[16] << 8) | sense_buffer[17]);
 
935
                    r += my_snprintf(b + r, blen - r, "  Sense Key Specific: "
 
936
                             "Error in %s byte %d",
 
937
                             ((sense_buffer[15] & 0x40) ? "Command" : "Data"),
 
938
                             (sense_buffer[16] << 8) | sense_buffer[17]);
855
939
                    if (sense_buffer[15] & 0x08)
856
 
                        r += sprintf(b + r, " bit %d\n",
857
 
                                     sense_buffer[15] & 0x07);
 
940
                        r += my_snprintf(b + r, blen - r, " bit %d\n",
 
941
                                         sense_buffer[15] & 0x07);
858
942
                    else
859
 
                        r += sprintf(b + r, "\n");
 
943
                        r += my_snprintf(b + r, blen - r, "\n");
860
944
                    break;
861
945
                case SPC_SK_NO_SENSE:
862
946
                case SPC_SK_NOT_READY:
863
947
                    progress = (sense_buffer[16] << 8) + sense_buffer[17];
864
948
                    pr = (progress * 100) / 65536;
865
 
                    rem = ((progress * 100) % 65536) / 655;
866
 
                    r += sprintf(b + r, "  Progress indication: %d.%02d%%\n",
867
 
                                 pr, rem);
 
949
                    rem = ((progress * 100) % 65536) / 656;
 
950
                    r += my_snprintf(b + r, blen - r, "  Progress "
 
951
                                     "indication: %d.%02d%%\n", pr, rem);
868
952
                    break;
869
953
                case SPC_SK_HARDWARE_ERROR:
870
954
                case SPC_SK_MEDIUM_ERROR:
871
955
                case SPC_SK_RECOVERED_ERROR:
872
 
                    r += sprintf(b + r, "  Actual retry count: "
873
 
                                 "0x%02x%02x\n", sense_buffer[16],
874
 
                                 sense_buffer[17]);
 
956
                    r += my_snprintf(b + r, blen - r, "  Actual retry count: "
 
957
                                     "0x%02x%02x\n", sense_buffer[16],
 
958
                                     sense_buffer[17]);
875
959
                    break;
876
960
                case SPC_SK_COPY_ABORTED:
877
 
                    r += sprintf(b + r, "  Segment pointer: ");
878
 
                    r += sprintf(b + r, "Relative to start of %s, byte %d",
879
 
                                 (sense_buffer[15] & 0x20) ?
880
 
                                     "segment descriptor" : "parameter list",
881
 
                                 (sense_buffer[16] << 8) + sense_buffer[17]);
 
961
                    r += my_snprintf(b + r, blen - r, "  Segment pointer: ");
 
962
                    r += my_snprintf(b + r, blen - r, "Relative to start of "
 
963
                                     "%s, byte %d",
 
964
                                     ((sense_buffer[15] & 0x20) ?
 
965
                                      "segment descriptor" : "parameter list"),
 
966
                                     ((sense_buffer[16] << 8) +
 
967
                                      sense_buffer[17]));
882
968
                    if (sense_buffer[15] & 0x08)
883
 
                        r += sprintf(b + r, " bit %d\n",
884
 
                                     sense_buffer[15] & 0x07);
 
969
                        r += my_snprintf(b + r, blen - r, " bit %d\n",
 
970
                                         sense_buffer[15] & 0x07);
885
971
                    else
886
 
                        r += sprintf(b + r, "\n");
 
972
                        r += my_snprintf(b + r, blen - r, "\n");
887
973
                    break;
888
974
                case SPC_SK_UNIT_ATTENTION:
889
 
                    r += sprintf(b + r, "  Unit attention condition queue: ");
890
 
                    r += sprintf(b + r, "overflow flag is %d\n",
891
 
                                 !!(sense_buffer[15] & 0x1));
 
975
                    r += my_snprintf(b + r, blen - r, "  Unit attention "
 
976
                                     "condition queue: ");
 
977
                    r += my_snprintf(b + r, blen - r, "overflow flag is %d\n",
 
978
                                     !!(sense_buffer[15] & 0x1));
892
979
                    break;
893
980
                default:
894
 
                    r += sprintf(b + r, "  Sense_key: 0x%x unexpected\n",
895
 
                                 ssh.sense_key);
 
981
                    r += my_snprintf(b + r, blen - r, "  Sense_key: 0x%x "
 
982
                                     "unexpected\n", ssh.sense_key);
896
983
                    break;
897
984
                }
898
985
            }
899
 
            if (r > 0) {
900
 
                n += snprintf(buff + n, buff_len - n, "%s", b);
901
 
                if (n >= buff_len)
902
 
                    return;
903
 
            }
904
 
        } else {
905
 
            n += snprintf(buff + n, buff_len - n, " fixed descriptor "
906
 
                          "length too short, len=%d\n", len);
907
 
            if (n >= buff_len)
908
 
                return;
909
 
        }
 
986
            if (r > 0)
 
987
                n += my_snprintf(buff + n, buff_len - n, "%s", b);
 
988
        } else
 
989
            n += my_snprintf(buff + n, buff_len - n, " fixed descriptor "
 
990
                             "length too short, len=%d\n", len);
910
991
    } else {    /* non-extended SCSI-1 sense data ?? */
911
992
        if (sb_len < 4) {
912
 
            n += snprintf(buff + n, buff_len - n, "sense buffer too short "
913
 
                          "(4 byte minimum)\n");
 
993
            n += my_snprintf(buff + n, buff_len - n, "sense buffer too short "
 
994
                             "(4 byte minimum)\n");
914
995
            return;
915
996
        }
916
997
        r = 0;
917
 
        r += sprintf(b + r, "Probably uninitialized data.\n  Try to view "
918
 
                     "as SCSI-1 non-extended sense:\n");
919
 
        r += sprintf(b + r, "  AdValid=%d  Error class=%d  Error code=%d\n",
920
 
                     !!(sense_buffer[0] & 0x80),
921
 
                     ((sense_buffer[0] >> 4) & 0x7),
922
 
                     (sense_buffer[0] & 0xf));
 
998
        r += my_snprintf(b + r, blen - r, "Probably uninitialized data.\n  "
 
999
                         "Try to view as SCSI-1 non-extended sense:\n");
 
1000
        r += my_snprintf(b + r, blen - r, "  AdValid=%d  Error class=%d  "
 
1001
                         "Error code=%d\n", !!(sense_buffer[0] & 0x80),
 
1002
                         ((sense_buffer[0] >> 4) & 0x7),
 
1003
                         (sense_buffer[0] & 0xf));
923
1004
        if (sense_buffer[0] & 0x80)
924
 
            r += sprintf(b + r, "  lba=0x%x\n",
925
 
                         ((sense_buffer[1] & 0x1f) << 16) +
926
 
                         (sense_buffer[2] << 8) + sense_buffer[3]);
927
 
        n += snprintf(buff + n, buff_len - n, "%s\n", b);
928
 
        if (n >= buff_len)
929
 
            return;
 
1005
            r += my_snprintf(b + r, blen - r, "  lba=0x%x\n",
 
1006
                             ((sense_buffer[1] & 0x1f) << 16) +
 
1007
                             (sense_buffer[2] << 8) + sense_buffer[3]);
 
1008
        n += my_snprintf(buff + n, buff_len - n, "%s\n", b);
930
1009
        len = sb_len;
931
1010
        if (len > 32)
932
1011
            len = 32;   /* trim in case there is a lot of rubbish */
933
1012
    }
934
1013
    if (raw_sinfo) {
935
 
        n += snprintf(buff + n, buff_len - n, " Raw sense data (in hex):\n");
936
 
        if (n >= buff_len)
 
1014
        n += my_snprintf(buff + n, buff_len - n, " Raw sense data (in hex):"
 
1015
                         "\n");
 
1016
        if (n >= (buff_len - 1))
937
1017
            return;
938
1018
        dStrHexErr((const char *)sense_buffer, len, buff_len - n, buff + n);
939
1019
    }
944
1024
sg_print_sense(const char * leadin, const unsigned char * sense_buffer,
945
1025
               int sb_len, int raw_sinfo)
946
1026
{
947
 
    char b[1024];
 
1027
    char b[2048];
948
1028
 
949
1029
    sg_get_sense_str(leadin, sense_buffer, sb_len, raw_sinfo, sizeof(b), b);
950
1030
    if (NULL == sg_warnings_strm)
952
1032
    fprintf(sg_warnings_strm, "%s", b);
953
1033
}
954
1034
 
 
1035
/* See description in sg_lib.h header file */
955
1036
int
956
1037
sg_scsi_normalize_sense(const unsigned char * sensep, int sb_len,
957
1038
                        struct sg_scsi_sense_hdr * sshp)
1052
1133
 
1053
1134
    if ((NULL == buff) || (buff_len < 1))
1054
1135
        return;
 
1136
    else if (1 == buff_len) {
 
1137
        buff[0] = '\0';
 
1138
        return;
 
1139
    }
1055
1140
    if (NULL == cmdp) {
1056
 
        strncpy(buff, "<null> command pointer", buff_len);
 
1141
        my_snprintf(buff, buff_len, "%s", "<null> command pointer");
1057
1142
        return;
1058
1143
    }
1059
1144
    service_action = (SG_VARIABLE_LENGTH_CMD == cmdp[0]) ?
1060
 
                     (cmdp[1] & 0x1f) : ((cmdp[8] << 8) | cmdp[9]);
 
1145
                     ((cmdp[8] << 8) | cmdp[9]) : (cmdp[1] & 0x1f);
1061
1146
    sg_get_opcode_sa_name(cmdp[0], service_action, peri_type, buff_len, buff);
1062
1147
}
1063
1148
 
1070
1155
 
1071
1156
    if ((NULL == buff) || (buff_len < 1))
1072
1157
        return;
 
1158
    else if (1 == buff_len) {
 
1159
        buff[0] = '\0';
 
1160
        return;
 
1161
    }
1073
1162
    switch ((int)cmd_byte0) {
1074
1163
    case SG_VARIABLE_LENGTH_CMD:
1075
1164
        vnp = get_value_name(sg_lib_variable_length_arr, service_action,
1076
1165
                             peri_type);
1077
1166
        if (vnp)
1078
 
            strncpy(buff, vnp->name, buff_len);
 
1167
            my_snprintf(buff, buff_len, "%s", vnp->name);
1079
1168
        else
1080
 
            snprintf(buff, buff_len, "Variable length service action=0x%x",
1081
 
                     service_action);
 
1169
            my_snprintf(buff, buff_len, "Variable length service action=0x%x",
 
1170
                        service_action);
1082
1171
        break;
1083
1172
    case SG_MAINTENANCE_IN:
1084
1173
        vnp = get_value_name(sg_lib_maint_in_arr, service_action, peri_type);
1085
1174
        if (vnp)
1086
 
            strncpy(buff, vnp->name, buff_len);
 
1175
            my_snprintf(buff, buff_len, "%s", vnp->name);
1087
1176
        else
1088
 
            snprintf(buff, buff_len, "Maintenance in service action=0x%x",
1089
 
                     service_action);
 
1177
            my_snprintf(buff, buff_len, "Maintenance in service action=0x%x",
 
1178
                        service_action);
1090
1179
        break;
1091
1180
    case SG_MAINTENANCE_OUT:
1092
1181
        vnp = get_value_name(sg_lib_maint_out_arr, service_action, peri_type);
1093
1182
        if (vnp)
1094
 
            strncpy(buff, vnp->name, buff_len);
 
1183
            my_snprintf(buff, buff_len, "%s", vnp->name);
1095
1184
        else
1096
 
            snprintf(buff, buff_len, "Maintenance out service action=0x%x",
1097
 
                     service_action);
 
1185
            my_snprintf(buff, buff_len, "Maintenance out service action=0x%x",
 
1186
                        service_action);
1098
1187
        break;
1099
1188
    case SG_SERVICE_ACTION_IN_12:
1100
1189
        vnp = get_value_name(sg_lib_serv_in12_arr, service_action, peri_type);
1101
1190
        if (vnp)
1102
 
            strncpy(buff, vnp->name, buff_len);
 
1191
            my_snprintf(buff, buff_len, "%s", vnp->name);
1103
1192
        else
1104
 
            snprintf(buff, buff_len, "Service action in(12)=0x%x",
1105
 
                     service_action);
 
1193
            my_snprintf(buff, buff_len, "Service action in(12)=0x%x",
 
1194
                        service_action);
1106
1195
        break;
1107
1196
    case SG_SERVICE_ACTION_OUT_12:
1108
1197
        vnp = get_value_name(sg_lib_serv_out12_arr, service_action, peri_type);
1109
1198
        if (vnp)
1110
 
            strncpy(buff, vnp->name, buff_len);
 
1199
            my_snprintf(buff, buff_len, "%s", vnp->name);
1111
1200
        else
1112
 
            snprintf(buff, buff_len, "Service action out(12)=0x%x",
1113
 
                     service_action);
 
1201
            my_snprintf(buff, buff_len, "Service action out(12)=0x%x",
 
1202
                        service_action);
1114
1203
        break;
1115
1204
    case SG_SERVICE_ACTION_IN_16:
1116
1205
        vnp = get_value_name(sg_lib_serv_in16_arr, service_action, peri_type);
1117
1206
        if (vnp)
1118
 
            strncpy(buff, vnp->name, buff_len);
 
1207
            my_snprintf(buff, buff_len, "%s", vnp->name);
1119
1208
        else
1120
 
            snprintf(buff, buff_len, "Service action in(16)=0x%x",
1121
 
                     service_action);
 
1209
            my_snprintf(buff, buff_len, "Service action in(16)=0x%x",
 
1210
                        service_action);
1122
1211
        break;
1123
1212
    case SG_SERVICE_ACTION_OUT_16:
1124
1213
        vnp = get_value_name(sg_lib_serv_out16_arr, service_action, peri_type);
1125
1214
        if (vnp)
1126
 
            strncpy(buff, vnp->name, buff_len);
 
1215
            my_snprintf(buff, buff_len, "%s", vnp->name);
1127
1216
        else
1128
 
            snprintf(buff, buff_len, "Service action out(16)=0x%x",
1129
 
                     service_action);
 
1217
            my_snprintf(buff, buff_len, "Service action out(16)=0x%x",
 
1218
                        service_action);
1130
1219
        break;
1131
1220
    case SG_PERSISTENT_RESERVE_IN:
1132
1221
        vnp = get_value_name(sg_lib_pr_in_arr, service_action, peri_type);
1133
1222
        if (vnp)
1134
 
            strncpy(buff, vnp->name, buff_len);
 
1223
            my_snprintf(buff, buff_len, "%s", vnp->name);
1135
1224
        else
1136
 
            snprintf(buff, buff_len, "Persistent reserve in, service "
1137
 
                     "action=0x%x", service_action);
 
1225
            my_snprintf(buff, buff_len, "Persistent reserve in, service "
 
1226
                        "action=0x%x", service_action);
1138
1227
        break;
1139
1228
    case SG_PERSISTENT_RESERVE_OUT:
1140
1229
        vnp = get_value_name(sg_lib_pr_out_arr, service_action, peri_type);
1141
1230
        if (vnp)
1142
 
            strncpy(buff, vnp->name, buff_len);
1143
 
        else
1144
 
            snprintf(buff, buff_len, "Persistent reserve out, service "
1145
 
                     "action=0x%x", service_action);
 
1231
            my_snprintf(buff, buff_len, "%s", vnp->name);
 
1232
        else
 
1233
            my_snprintf(buff, buff_len, "Persistent reserve out, service "
 
1234
                        "action=0x%x", service_action);
 
1235
        break;
 
1236
    case SG_EXTENDED_COPY:
 
1237
        vnp = get_value_name(sg_lib_xcopy_sa_arr, service_action, peri_type);
 
1238
        if (vnp)
 
1239
            my_snprintf(buff, buff_len, "%s", vnp->name);
 
1240
        else
 
1241
            my_snprintf(buff, buff_len, "Extended copy, service action=0x%x",
 
1242
                        service_action);
 
1243
        break;
 
1244
    case SG_RECEIVE_COPY:
 
1245
        vnp = get_value_name(sg_lib_rec_copy_sa_arr, service_action,
 
1246
                             peri_type);
 
1247
        if (vnp)
 
1248
            my_snprintf(buff, buff_len, "%s", vnp->name);
 
1249
        else
 
1250
            my_snprintf(buff, buff_len, "Receive copy, service action=0x%x",
 
1251
                        service_action);
 
1252
        break;
 
1253
    case SG_READ_BUFFER:
 
1254
        /* spc4r34 requested treating mode as service action */
 
1255
        vnp = get_value_name(sg_lib_read_buff_arr, service_action,
 
1256
                             peri_type);
 
1257
        if (vnp)
 
1258
            my_snprintf(buff, buff_len, "Read buffer (%s)\n", vnp->name);
 
1259
        else
 
1260
            my_snprintf(buff, buff_len, "Read buffer, mode=0x%x",
 
1261
                        service_action);
 
1262
        break;
 
1263
    case SG_WRITE_BUFFER:
 
1264
        /* spc4r34 requested treating mode as service action */
 
1265
        vnp = get_value_name(sg_lib_write_buff_arr, service_action,
 
1266
                             peri_type);
 
1267
        if (vnp)
 
1268
            my_snprintf(buff, buff_len, "Write buffer (%s)\n", vnp->name);
 
1269
        else
 
1270
            my_snprintf(buff, buff_len, "Write buffer, mode=0x%x",
 
1271
                        service_action);
1146
1272
        break;
1147
1273
    default:
1148
1274
        sg_get_opcode_name(cmd_byte0, peri_type, buff_len, buff);
1159
1285
 
1160
1286
    if ((NULL == buff) || (buff_len < 1))
1161
1287
        return;
 
1288
    else if (1 == buff_len) {
 
1289
        buff[0] = '\0';
 
1290
        return;
 
1291
    }
1162
1292
    if (SG_VARIABLE_LENGTH_CMD == cmd_byte0) {
1163
 
        strncpy(buff, "Variable length", buff_len);
 
1293
        my_snprintf(buff, buff_len, "%s", "Variable length");
1164
1294
        return;
1165
1295
    }
1166
1296
    grp = (cmd_byte0 >> 5) & 0x7;
1172
1302
    case 5:
1173
1303
        vnp = get_value_name(sg_lib_normal_opcodes, cmd_byte0, peri_type);
1174
1304
        if (vnp)
1175
 
            strncpy(buff, vnp->name, buff_len);
 
1305
            my_snprintf(buff, buff_len, "%s", vnp->name);
1176
1306
        else
1177
 
            snprintf(buff, buff_len, "Opcode=0x%x", (int)cmd_byte0);
 
1307
            my_snprintf(buff, buff_len, "Opcode=0x%x", (int)cmd_byte0);
1178
1308
        break;
1179
1309
    case 3:
1180
 
        snprintf(buff, buff_len, "Reserved [0x%x]", (int)cmd_byte0);
 
1310
        my_snprintf(buff, buff_len, "Reserved [0x%x]", (int)cmd_byte0);
1181
1311
        break;
1182
1312
    case 6:
1183
1313
    case 7:
1184
 
        snprintf(buff, buff_len, "Vendor specific [0x%x]", (int)cmd_byte0);
 
1314
        my_snprintf(buff, buff_len, "Vendor specific [0x%x]", (int)cmd_byte0);
1185
1315
        break;
1186
1316
    default:
1187
 
        snprintf(buff, buff_len, "Opcode=0x%x", (int)cmd_byte0);
 
1317
        my_snprintf(buff, buff_len, "Opcode=0x%x", (int)cmd_byte0);
1188
1318
        break;
1189
1319
    }
1190
1320
}
1244
1374
    errstr = strerror(errnum);
1245
1375
    if (NULL == errstr) {
1246
1376
        len = strlen(safe_errbuf);
1247
 
        snprintf(safe_errbuf + len, sizeof(safe_errbuf) - len, "%i", errnum);
1248
 
        safe_errbuf[sizeof(safe_errbuf) - 1] = '\0';  /* bombproof */
 
1377
        my_snprintf(safe_errbuf + len, sizeof(safe_errbuf) - len, "%i",
 
1378
                    errnum);
1249
1379
        return safe_errbuf;
1250
1380
    }
1251
1381
    return errstr;
1270
1400
    const int cpstart = 60;
1271
1401
    int cpos = cpstart;
1272
1402
    int bpos = bpstart;
1273
 
    int i, k;
 
1403
    int i, k, blen;
1274
1404
 
1275
1405
    if (len <= 0)
1276
1406
        return;
 
1407
    blen = (int)sizeof(buff);
1277
1408
    formatstr = (0 == no_ascii) ? "%.76s\n" : "%.56s\n";
1278
1409
    memset(buff, ' ', 80);
1279
1410
    buff[80] = '\0';
1283
1414
            bpos += 3;
1284
1415
            if (bpos == (bpstart + (9 * 3)))
1285
1416
                bpos++;
1286
 
            sprintf(&buff[bpos], "%.2x", (int)(unsigned char)c);
 
1417
            my_snprintf(&buff[bpos], blen - bpos, "%.2x",
 
1418
                        (int)(unsigned char)c);
1287
1419
            buff[bpos + 2] = ' ';
1288
1420
            if ((k > 0) && (0 == ((k + 1) % 16))) {
1289
1421
                printf(formatstr, buff);
1298
1430
        return;
1299
1431
    }
1300
1432
    /* no_ascii>=0, start each line with address (offset) */
1301
 
    k = sprintf(buff + 1, "%.2x", a);
 
1433
    k = my_snprintf(buff + 1, blen - 1, "%.2x", a);
1302
1434
    buff[k + 1] = ' ';
1303
1435
 
1304
1436
    for (i = 0; i < len; i++) {
1306
1438
        bpos += 3;
1307
1439
        if (bpos == (bpstart + (9 * 3)))
1308
1440
            bpos++;
1309
 
        sprintf(&buff[bpos], "%.2x", (int)(unsigned char)c);
 
1441
        my_snprintf(&buff[bpos], blen - bpos, "%.2x", (int)(unsigned char)c);
1310
1442
        buff[bpos + 2] = ' ';
1311
1443
        if (no_ascii)
1312
1444
            buff[cpos++] = ' ';
1321
1453
            cpos = cpstart;
1322
1454
            a += 16;
1323
1455
            memset(buff, ' ', 80);
1324
 
            k = sprintf(buff + 1, "%.2x", a);
 
1456
            k = my_snprintf(buff + 1, blen - 1, "%.2x", a);
1325
1457
            buff[k + 1] = ' ';
1326
1458
        }
1327
1459
    }
1353
1485
        bpos += 3;
1354
1486
        if (bpos == (bpstart + (9 * 3)))
1355
1487
            bpos++;
1356
 
        sprintf(&buff[bpos], "%.2x", (int)(unsigned char)c);
 
1488
        my_snprintf(&buff[bpos], (int)sizeof(buff) - bpos, "%.2x",
 
1489
                    (int)(unsigned char)c);
1357
1490
        buff[bpos + 2] = ' ';
1358
1491
        if ((k > 0) && (0 == ((k + 1) % 16))) {
1359
 
            n += snprintf(b + n, b_len - n, "%.60s\n", buff);
1360
 
            if (n >= b_len)
 
1492
            n += my_snprintf(b + n, b_len - n, "%.60s\n", buff);
 
1493
            if (n >= (b_len - 1))
1361
1494
                return;
1362
1495
            bpos = bpstart;
1363
1496
            memset(buff, ' ', 80);
1364
1497
        }
1365
1498
    }
1366
1499
    if (bpos > bpstart)
1367
 
        n += snprintf(b + n, b_len - n, "%.60s\n", buff);
 
1500
        n += my_snprintf(b + n, b_len - n, "%.60s\n", buff);
1368
1501
    return;
1369
1502
}
1370
1503
 
1416
1549
    const int cpstart = 52;
1417
1550
    int cpos = cpstart;
1418
1551
    int bpos = bpstart;
1419
 
    int i, k;
 
1552
    int i, k, blen;
1420
1553
 
1421
1554
    if (num <= 0)
1422
1555
        return;
 
1556
    blen = (int)sizeof(buff);
1423
1557
    memset(buff, ' ', 80);
1424
1558
    buff[80] = '\0';
1425
1559
    if (no_ascii < 0) {
1428
1562
            if (swapb)
1429
1563
                c = swapb_ushort(c);
1430
1564
            bpos += 5;
1431
 
            sprintf(&buff[bpos], "%.4x", (unsigned int)c);
 
1565
            my_snprintf(&buff[bpos], blen - bpos, "%.4x", (unsigned int)c);
1432
1566
            buff[bpos + 4] = ' ';
1433
1567
            if ((k > 0) && (0 == ((k + 1) % 8))) {
1434
1568
                if (-2 == no_ascii)
1448
1582
        return;
1449
1583
    }
1450
1584
    /* no_ascii>=0, start each line with address (offset) */
1451
 
    k = sprintf(buff + 1, "%.2x", a);
 
1585
    k = my_snprintf(buff + 1, blen - 1, "%.2x", a);
1452
1586
    buff[k + 1] = ' ';
1453
1587
 
1454
1588
    for (i = 0; i < num; i++) {
1456
1590
        if (swapb)
1457
1591
            c = swapb_ushort(c);
1458
1592
        bpos += 5;
1459
 
        sprintf(&buff[bpos], "%.4x", (unsigned int)c);
 
1593
        my_snprintf(&buff[bpos], blen - bpos, "%.4x", (unsigned int)c);
1460
1594
        buff[bpos + 4] = ' ';
1461
1595
        if (no_ascii) {
1462
1596
            buff[cpos++] = ' ';
1479
1613
            cpos = cpstart;
1480
1614
            a += 8;
1481
1615
            memset(buff, ' ', 80);
1482
 
            k = sprintf(buff + 1, "%.2x", a);
 
1616
            k = my_snprintf(buff + 1, blen - 1, "%.2x", a);
1483
1617
            buff[k + 1] = ' ';
1484
1618
        }
1485
1619
    }
1552
1686
                return num * 1073741824;
1553
1687
            return -1;
1554
1688
        case 'X':
1555
 
            cp = strchr(buf, 'x');
 
1689
            cp = (char *)strchr(buf, 'x');
1556
1690
            if (NULL == cp)
1557
 
                cp = strchr(buf, 'X');
 
1691
                cp = (char *)strchr(buf, 'X');
1558
1692
            if (cp) {
1559
1693
                n = sg_get_num(cp + 1);
1560
1694
                if (-1 != n)
1579
1713
{
1580
1714
    int res, len, num;
1581
1715
    unsigned int unum;
1582
 
    const char * commap;
 
1716
    char * commap;
1583
1717
 
1584
1718
    if ((NULL == buf) || ('\0' == buf[0]))
1585
1719
        return -1;
1586
1720
    len = strlen(buf);
1587
 
    commap = strchr(buf + 1, ',');
 
1721
    commap = (char *)strchr(buf + 1, ',');
1588
1722
    if (('0' == buf[0]) && (('x' == buf[1]) || ('X' == buf[1]))) {
1589
1723
        res = sscanf(buf + 2, "%x", &unum);
1590
1724
        num = unum;
1684
1818
                return num * 1099511627776LL * 1024;
1685
1819
            return -1LL;
1686
1820
        case 'X':
1687
 
            cp = strchr(buf, 'x');
 
1821
            cp = (char *)strchr(buf, 'x');
1688
1822
            if (NULL == cp)
1689
 
                cp = strchr(buf, 'X');
 
1823
                cp = (char *)strchr(buf, 'X');
1690
1824
            if (cp) {
1691
1825
                ll = sg_get_llnum(cp + 1);
1692
1826
                if (-1LL != ll)
1778
1912
}
1779
1913
 
1780
1914
#endif
1781