/* <string> getenv false */ static int zgetenv(i_ctx_t *i_ctx_p) { os_ptr op = osp; char *str; byte *value; int len = 0; check_read_type(*op, t_string); str = ref_to_string(op, imemory, "getenv key"); if (str == 0) return_error(e_VMerror); if (gp_getenv(str, (char *)0, &len) > 0) { /* key missing */ ifree_string((byte *) str, r_size(op) + 1, "getenv key"); make_false(op); return 0; } value = ialloc_string(len, "getenv value"); if (value == 0) { ifree_string((byte *) str, r_size(op) + 1, "getenv key"); return_error(e_VMerror); } DISCARD(gp_getenv(str, (char *)value, &len)); /* can't fail */ ifree_string((byte *) str, r_size(op) + 1, "getenv key"); /* Delete the stupid C string terminator. */ value = iresize_string(value, len, len - 1, "getenv value"); /* can't fail */ push(1); make_string(op - 1, a_all | icurrent_space, len - 1, value); make_true(op); return 0; }
ENUM_PTRS_END static RELOC_PTRS_WITH(TExecution_Context_reloc_ptrs, TExecution_Context *mptr) { RELOC_PTR(TExecution_Context, current_face); /* RELOC_PTR(TExecution_Context, code); // local, no gc invocations */ RELOC_PTR(TExecution_Context, FDefs); RELOC_PTR(TExecution_Context, IDefs); /* RELOC_PTR(TExecution_Context, glyphIns); // Never used. */ RELOC_PTR(TExecution_Context, callStack); RELOC_PTR(TExecution_Context, codeRangeTable[0].Base); RELOC_PTR(TExecution_Context, codeRangeTable[1].Base); RELOC_PTR(TExecution_Context, codeRangeTable[2].Base); RELOC_PTR(TExecution_Context, storage); RELOC_PTR(TExecution_Context, stack); /* zp0, // local, no gc invocations */ /* zp1, // local, no gc invocations */ /* zp2, // local, no gc invocations */ RELOC_PTR(TExecution_Context, pts.org_x); RELOC_PTR(TExecution_Context, pts.org_y); RELOC_PTR(TExecution_Context, pts.cur_x); RELOC_PTR(TExecution_Context, pts.cur_y); RELOC_PTR(TExecution_Context, pts.touch); RELOC_PTR(TExecution_Context, pts.contours); RELOC_PTR(TExecution_Context, twilight.org_x); RELOC_PTR(TExecution_Context, twilight.org_y); RELOC_PTR(TExecution_Context, twilight.cur_x); RELOC_PTR(TExecution_Context, twilight.cur_y); RELOC_PTR(TExecution_Context, twilight.touch); RELOC_PTR(TExecution_Context, twilight.contours); RELOC_PTR(TExecution_Context, cvt); RELOC_PTR(TExecution_Context, memory); DISCARD(mptr); }
/* - .defaultpapersize false */ static int zdefaultpapersize(i_ctx_t *i_ctx_p) { os_ptr op = osp; byte *value; int len = 0; if (gp_defaultpapersize((char *)0, &len) > 0) { /* no default paper size */ push(1); make_false(op); return 0; } value = ialloc_string(len, "defaultpapersize value"); if (value == 0) { return_error(e_VMerror); } DISCARD(gp_defaultpapersize((char *)value, &len)); /* can't fail */ /* Delete the stupid C string terminator. */ value = iresize_string(value, len, len - 1, "defaultpapersize value"); /* can't fail */ push(2); make_string(op - 1, a_all | icurrent_space, len - 1, value); make_true(op); return 0; }
bp_Caption * bp_parseCaption(bp_Context * context, xmlNodePtr node) { bp_Caption * result = malloc(sizeof(bp_Caption)); xmlAttrPtr attr; xmlNodePtr child; bp_initNode(&result->node, BPE_CAPTION); result->inlineAttr = *(context->inlineAttr); for (attr = node->properties; attr; attr = attr->next) { bp_parseInlineAttribute(context, &result->inlineAttr, attr); } child = node->children; if (ELEM(child) == BPE_TEXT) { int len; len = strlen(child->content); result->text = malloc(++len); memcpy(result->text, child->children, len); } else { DISCARD(child); } return result; }
/* Wrapper procedure called to start the new thread. */ static void * gp_thread_begin_wrapper(void *thread_data /* gp_thread_creation_closure_t * */) { gp_thread_creation_closure_t closure; closure = *(gp_thread_creation_closure_t *)thread_data; free(thread_data); DISCARD(closure.proc(closure.proc_data)); return NULL; /* return value is ignored */ }
static ENUM_PTRS_WITH(gx_ttfReader_enum_ptrs, gx_ttfReader *mptr) { /* The fields 'pfont' and 'glyph_data' may contain pointers from global to local memory ( see a comment in gxttfb.h). They must be NULL when a garbager is invoked. Due to that we don't enumerate and don't relocate them. */ DISCARD(mptr); return 0; }
void bp_parseInlineContent(bp_Context * context, bp_Node * const parent, xmlNodePtr node) { xmlNodePtr child; for (child = node->children; child; child = child->next) { switch (ELEM(child)) { case BPE_TEXT: ADD(bp_parseText(context, child)); break; case BPE_INLINE: ADD(bp_parseInline(context, child)); break; case BPE_LABEL: ADD(bp_parseLabel(context, child)); break; case BPE_REF: ADD(bp_parseRef(context, child)); break; default: DISCARD(child); } } }
/* Write one code map. */ static int cmap_put_code_map(const gs_memory_t *mem, stream *s, int which, const gs_cmap_t *pcmap, const cmap_operators_t *pcmo, psf_put_name_chars_proc_t put_name_chars, int font_index_only) { /* For simplicity, produce one entry for each lookup range. */ gs_cmap_lookups_enum_t lenum; int font_index = (pcmap->num_fonts <= 1 ? 0 : -1); int code; for (gs_cmap_lookups_enum_init(pcmap, which, &lenum); (code = gs_cmap_enum_next_lookup(&lenum)) == 0; ) { gs_cmap_lookups_enum_t counter; int num_entries = 0; int gi; if (font_index_only >= 0 && lenum.entry.font_index != font_index_only) continue; if (font_index_only < 0 && lenum.entry.font_index != font_index) { pprintd1(s, "%d usefont\n", lenum.entry.font_index); font_index = lenum.entry.font_index; } /* Count the number of entries in this lookup range. */ counter = lenum; while (gs_cmap_enum_next_entry(&counter) == 0) ++num_entries; for (gi = 0; gi < num_entries; gi += 100) { int i = gi, ni = min(i + 100, num_entries); const char *end; pprintd1(s, "%d ", ni - i); if (lenum.entry.key_is_range) { if (lenum.entry.value_type == CODE_VALUE_CID || lenum.entry.value_type == CODE_VALUE_NOTDEF) { stream_puts(s, pcmo->beginrange); end = pcmo->endrange; } else { /* must be def, not notdef */ stream_puts(s, "beginbfrange\n"); end = "endbfrange\n"; } } else { if (lenum.entry.value_type == CODE_VALUE_CID || lenum.entry.value_type == CODE_VALUE_NOTDEF) { stream_puts(s, pcmo->beginchar); end = pcmo->endchar; } else { /* must be def, not notdef */ stream_puts(s, "beginbfchar\n"); end = "endbfchar\n"; } } for (; i < ni; ++i) { int j; long value; int value_size; DISCARD(gs_cmap_enum_next_entry(&lenum)); /* can't fail */ value_size = lenum.entry.value.size; for (j = 0; j <= lenum.entry.key_is_range; ++j) { stream_putc(s, '<'); pput_hex(s, lenum.entry.key[j], lenum.entry.key_size); stream_putc(s, '>'); } for (j = 0, value = 0; j < value_size; ++j) value = (value << 8) + lenum.entry.value.data[j]; switch (lenum.entry.value_type) { case CODE_VALUE_CID: case CODE_VALUE_NOTDEF: pprintld1(s, "%ld", value); break; case CODE_VALUE_CHARS: stream_putc(s, '<'); pput_hex(s, lenum.entry.value.data, value_size); stream_putc(s, '>'); break; case CODE_VALUE_GLYPH: { gs_const_string str; int code = pcmap->glyph_name(mem, (gs_glyph)value, &str, pcmap->glyph_name_data); if (code < 0) return code; stream_putc(s, '/'); code = put_name_chars(s, str.data, str.size); if (code < 0) return code; } break; default: /* not possible */ return_error(gs_error_unregistered); } stream_putc(s, '\n'); } stream_puts(s, end); } } return code; }
void gp_set_file_binary(int prnfno, int binary) { DISCARD(setmode_binary(prnfno, binary != 0)); }
/* * Combine a file name with a prefix. * Concatenates two paths and reduce parent references and current * directory references from the concatenation when possible. * The trailing zero byte is being added. * * Returns "gp_combine_success" if OK and sets '*blen' to the length of * the combined string. If the combined string is too small for the buffer * length passed in (as defined by the initial value of *blen), then the * "gp_combine_small_buffer" code is returned. * * Also tolerates/skips leading IODevice specifiers such as %os% or %rom% * When there is a leading '%' in the 'fname' no other processing is done. * * Examples : * "/gs/lib" + "../Resource/CMap/H" --> "/gs/Resource/CMap/H" * "C:/gs/lib" + "../Resource/CMap/H" --> "C:/gs/Resource/CMap/H" * "hard disk:gs:lib" + "::Resource:CMap:H" --> * "hard disk:gs:Resource:CMap:H" * "DUA1:[GHOSTSCRIPT.LIB" + "-.RESOURCE.CMAP]H" --> * "DUA1:[GHOSTSCRIPT.RESOURCE.CMAP]H" * "\\server\share/a/b///c/../d.e/./" + "../x.e/././/../../y.z/v.v" --> * "\\server\share/a/y.z/v.v" * "%rom%lib/" + "gs_init.ps" --> "%rom%lib/gs_init.ps * "" + "%rom%lib/gs_init.ps" --> "%rom%lib/gs_init.ps" */ gp_file_name_combine_result gp_file_name_combine_generic(const char *prefix, uint plen, const char *fname, uint flen, bool no_sibling, char *buffer, uint *blen) { /* * THIS CODE IS SHARED FOR MULTIPLE PLATFORMS. * PLEASE DON'T CHANGE IT FOR A SPECIFIC PLATFORM. * Change gp_file_name_combine instead. */ char *bp = buffer, *bpe = buffer + *blen; const char *ip, *ipe; uint slen; uint infix_type = 0; /* 0=none, 1=current, 2=parent. */ uint infix_len = 0; uint rlen = gp_file_name_root(fname, flen); /* We need a special handling of infixes only immediately after a drive. */ if ( flen > 0 && fname[0] == '%') { /* IoDevice -- just return the fname as-is since this */ /* function only handles the default file system */ /* NOTE: %os% will subvert the normal processing of prefix and fname */ ip = fname; *blen = flen; if (!append(&bp, bpe, &ip, flen)) return gp_combine_small_buffer; return gp_combine_success; } if (rlen != 0) { /* 'fname' is absolute, ignore the prefix. */ ip = fname; ipe = fname + flen; } else { /* Concatenate with prefix. */ ip = prefix; ipe = prefix + plen; rlen = gp_file_name_root(prefix, plen); } if (!append(&bp, bpe, &ip, rlen)) return gp_combine_small_buffer; slen = gs_file_name_check_separator(bp, buffer - bp, bp); /* Backward search. */ if (rlen != 0 && slen == 0) { /* Patch it against names like "c:dir" on Windows. */ const char *sep = gp_file_name_directory_separator(); slen = strlen(sep); if (!append(&bp, bpe, &sep, slen)) return gp_combine_small_buffer; rlen += slen; } for (;;) { const char *item = ip; uint ilen; slen = search_separator(&ip, ipe, item, 1); ilen = ip - item; if (ilen == 0 && !gp_file_name_is_empty_item_meanful()) { ip += slen; slen = 0; } else if (gp_file_name_is_current(item, ilen)) { /* Skip the reference to 'current', except the starting one. * We keep the starting 'current' for platforms, which * require relative paths to start with it. */ if (bp == buffer) { if (!append(&bp, bpe, &item, ilen)) return gp_combine_small_buffer; infix_type = 1; infix_len = ilen; } else { ip += slen; slen = 0; } } else if (!gp_file_name_is_parent(item, ilen)) { if (!append(&bp, bpe, &item, ilen)) return gp_combine_small_buffer; /* The 'item' pointer is now broken; it may be restored using 'ilen'. */ } else if (bp == buffer + rlen + infix_len) { /* Input is a parent and the output only contains a root and an infix. */ if (rlen != 0) return gp_combine_cant_handle; switch (infix_type) { case 1: /* Replace the infix with parent. */ bp = buffer + rlen; /* Drop the old infix, if any. */ infix_len = 0; /* Falls through. */ case 0: /* We have no infix, start with parent. */ if ((no_sibling && ipe == fname + flen && flen != 0) || !gp_file_name_is_partent_allowed()) return gp_combine_cant_handle; /* Falls through. */ case 2: /* Append one more parent - falls through. */ DO_NOTHING; } if (!append(&bp, bpe, &item, ilen)) return gp_combine_small_buffer; infix_type = 2; infix_len += ilen; /* Recompute the separator length. We cannot use the old slen on Mac OS. */ slen = gs_file_name_check_separator(ip, ipe - ip, ip); } else { /* Input is a parent and the output continues after infix. */ /* Unappend the last separator and the last item. */ uint slen1 = gs_file_name_check_separator(bp, buffer + rlen - bp, bp); /* Backward search. */ char *bie = bp - slen1; bp = bie; DISCARD(search_separator((const char **)&bp, buffer + rlen, bp, -1)); /* The cast above quiets a gcc warning. We believe it's a bug in the compiler. */ /* Skip the input with separator. We cannot use slen on Mac OS. */ ip += gs_file_name_check_separator(ip, ipe - ip, ip); if (no_sibling) { const char *p = ip; DISCARD(search_separator(&p, ipe, ip, 1)); if (p - ip != bie - bp || memcmp(ip, bp, p - ip)) return gp_combine_cant_handle; } slen = 0; } if (slen) { if (bp == buffer + rlen + infix_len) infix_len += slen; if (!append(&bp, bpe, &ip, slen)) return gp_combine_small_buffer; } if (ip == ipe) { if (ipe == fname + flen) { /* All done. * Note that the case (prefix + plen == fname && flen == 0) * falls here without appending a separator. */ const char *zero=""; if (bp == buffer) { /* Must not return empty path. */ const char *current = gp_file_name_current(); int clen = strlen(current); if (!append(&bp, bpe, ¤t, clen)) return gp_combine_small_buffer; } *blen = bp - buffer; if (!append(&bp, bpe, &zero, 1)) return gp_combine_small_buffer; return gp_combine_success; } else { /* ipe == prefix + plen */ /* Switch to fname. */ ip = fname; ipe = fname + flen; if (slen == 0) { /* Insert a separator. */ const char *sep; slen = search_separator(&ip, ipe, fname, 1); sep = (slen != 0 ? gp_file_name_directory_separator() : gp_file_name_separator()); slen = strlen(sep); if (bp == buffer + rlen + infix_len) infix_len += slen; if (!append(&bp, bpe, &sep, slen)) return gp_combine_small_buffer; ip = fname; /* Switch to fname. */ } } } } }
bp_Table * bp_parseTable(bp_Context * context, xmlNodePtr node) { bp_Table * result = malloc(sizeof(bp_Table)); bp_Node * const parent = &result->node; xmlAttrPtr attr; xmlNodePtr child, grand; bp_pushBlockBorder(context); bp_pushBlockInside(context); bp_pushInline(context); bp_initNode(&result->node, BPE_TABLE); result->_float = bp_defaultFloatAttributes; result->blockOutside = *(context->blockOutside); result->caption = NULL; result->nCols = 0; result->nRows = 0; for (attr = node->properties; attr; attr = attr->next) { bp_parseFloatAttribute(context, &result->_float, attr); bp_parseBlockOutsideAttribute(context, &result->blockOutside, attr); bp_parseBlockBorderAttribute(context, context->blockBorder, attr); bp_parseBlockInsideAttribute(context, context->blockInside, attr); bp_parseInlineAttribute(context, context->inlineAttr, attr); } result->blockBorder = *(context->blockBorder); // shared with children for (child = node->children; child; child = child->next) { switch(ELEM(child)) { case BPE_TR: result->nRows++; break; case BPE_TC: result->nCols++; break; case BPE_CAPTION: result->caption = bp_parseCaption(context, child); default: DISCARD(child); } } if (result->nRows) { int * colHeights = NULL; int col, row = 0; result->nCols = 0; for (child = node->children; child; child = child->next) { if(ELEM(child) == BPE_TR) { bp_pushBlockBorder(context); bp_pushBlockInside(context); bp_pushInline(context); for (attr = child->properties; attr; attr = attr->next) { bp_parseBlockBorderAttribute(context, context->blockBorder, attr); bp_parseBlockInsideAttribute(context, context->blockInside, attr); bp_parseInlineAttribute(context, context->inlineAttr, attr); } col = 0; for (grand = child->children; grand; grand = grand->next) { while ((col < result->nCols) && (colHeights[col] >= row)) col++; if(ELEM(grand) == BPE_TD) { bp_Cell * cell = bp_parseCell(context, grand, row, col); ADD(cell); if (cell->endCol >= result->nCols) { result->nCols = cell->endCol + 1; colHeights = realloc(colHeights, result->nCols * sizeof(int)); } for (col=cell->startCol; col <= cell->endCol; col++) { colHeights[col] = cell->endRow; } } else { DISCARD(grand); } } bp_popBlockBorder(context); bp_popBlockInside(context); bp_popInline(context); row++; } } if(colHeights) free(colHeights); } else if (result->nCols) { int * rowWidths = NULL; int col = 0, row; result->nRows = 0; for (child = node->children; child; child = child->next) { if(ELEM(child) == BPE_TC) { bp_pushBlockBorder(context); bp_pushBlockInside(context); bp_pushInline(context); for (attr = child->properties; attr; attr = attr->next) { bp_parseBlockBorderAttribute(context, context->blockBorder, attr); bp_parseBlockInsideAttribute(context, context->blockInside, attr); bp_parseInlineAttribute(context, context->inlineAttr, attr); } row = 0; for (grand = child->children; grand; grand = grand->next) { while ((row < result->nRows) && (rowWidths[row] >= col)) row++; if(ELEM(grand) == BPE_TD) { bp_Cell * cell = bp_parseCell(context, grand, row, col); ADD(cell); if (cell->endRow >= result->nRows) { result->nRows = cell->endRow + 1; rowWidths = realloc(rowWidths, result->nRows * sizeof(int)); } for (row=cell->startRow; row <= cell->endRow; row++) { rowWidths[row] = cell->endCol; } } else { DISCARD(grand); } } bp_popBlockBorder(context); bp_popBlockInside(context); bp_popInline(context); col++; } } if(rowWidths) free(rowWidths); } bp_popBlockBorder(context); bp_popBlockInside(context); bp_popInline(context); return result; }
bp_Page * bp_parsePage(bp_Context * context, xmlNodePtr node) { bp_Page * result = malloc(sizeof(bp_Page)); bp_Node * const parent = &result->node; xmlAttrPtr attr; xmlNodePtr child; bp_pushBlockOutside(context); bp_pushBlockBorder(context); bp_pushBlockInside(context); bp_pushInline(context); bp_initNode(&result->node, BPE_PAGE); result->title = NULL; for (attr = node->properties; attr; attr = attr->next) { bp_parseBlockOutsideAttribute(context, context->blockOutside, attr); bp_parseBlockBorderAttribute(context, context->blockBorder, attr); bp_parseBlockInsideAttribute(context, context->blockInside, attr); bp_parseInlineAttribute(context, context->inlineAttr, attr); } for (child = node->children; child; child = child->next) { switch(ELEM(child)) { case BPE_TITLE: if (!result->title) { xmlNodePtr grandchild = child->children; if (ELEM(grandchild) == BPE_TEXT) { int len = strlen(grandchild->content); char * title_string = malloc(++len); memcpy(title_string, grandchild->content, len); result->title = title_string; } else { DISCARD(grandchild); } } else { DISCARD(child); } break; case BPE_REF: bp_parseNavRef(context, child, result); break; case BPE_BLOCK: ADD(bp_parseBlock(context, child)); break; case BPE_IMAGE: ADD(bp_parseImage(context, child)); break; case BPE_TABLE: ADD(bp_parseTable(context, child)); break; case BPE_LABEL: ADD(bp_parseLabel(context, child)); break; default: DISCARD(child); } } bp_popBlockOutside(context); bp_popBlockBorder(context); bp_popBlockInside(context); bp_popInline(context); return result; }
bp_Book * bp_parseBook(bp_Context * context, xmlNodePtr node) { bp_Book * result = malloc(sizeof(bp_Book)); bp_Node * const parent = &result->node; bp_Node * page; xmlAttrPtr attr; xmlNodePtr child; bp_Page ** pages; st_data * fontSym; context->blockOutside = (void *) &bp_defaultBlockOutsideAttributes; context->blockBorder = (void *) &bp_defaultBlockBorderAttributes; context->blockInside = (void *) &bp_defaultBlockInsideAttributes; context->inlineAttr = (void *) &bp_defaultInlineAttributes; bp_pushBlockOutside(context); bp_pushBlockBorder(context); bp_pushBlockInside(context); bp_pushInline(context); bp_initNode(&result->node, BPE_BOOK); result->width = 528; result->height = 320; result->background = load_texture_cache_deferred("textures/book1.bmp",0); fontSym = st_lookup (bp_fonts, "default"); if (fontSym != NULL) { result->fontFace = fontSym->num; } else { LOG_ERROR("FATAL: default font missing in font symbol table\n"); exit(1); } result->layout = BPL_BOOK; result->blockProgression = BPD_DOWN; result->inlineProgression = BPD_RIGHT; result->pages = NULL; result->nPages = 0; for (attr = node->properties; attr; attr = attr->next) { bp_parseBlockOutsideAttribute(context, context->blockOutside, attr); bp_parseBlockBorderAttribute(context, context->blockBorder, attr); bp_parseBlockInsideAttribute(context, context->blockInside, attr); bp_parseInlineAttribute(context, context->inlineAttr, attr); } for (child = node->children; child; child = child->next) { switch(ELEM(child)) { case BPE_PAGE: result->nPages++; ADD(bp_parsePage(context, child)); break; default: DISCARD(child); } } bp_popBlockOutside(context); bp_popBlockBorder(context); bp_popBlockInside(context); bp_popInline(context); /* create page index */ pages = calloc(result->nPages, sizeof(bp_Page *)); result->pages = pages; for (page = parent->children; page; page = page->next) { *pages++ = (bp_Page *) page; } return result; }
void mbadblocks(int argc, char **argv, int type) { unsigned int i; unsigned int startSector=2; unsigned int endSector=0; struct MainParam_t mp; Fs_t *Fs; Stream_t *Dir; int ret; char *filename = NULL; char c; unsigned int badClus; int sectorMode=0; int writeMode=0; while ((c = getopt(argc, argv, "i:s:cwS:E:")) != EOF) { switch(c) { case 'i': set_cmd_line_image(optarg, 0); break; case 'c': checkListTwice(filename); filename = strdup(optarg); break; case 's': checkListTwice(filename); filename = strdup(optarg); sectorMode = 1; break; case 'S': startSector = atol(optarg); break; case 'E': endSector = atol(optarg); break; case 'w': writeMode = 1; break; case 'h': usage(0); default: usage(1); } } if (argc != optind+1 || !argv[optind][0] || argv[optind][1] != ':' || argv[optind][2]) { usage(1); } init_mp(&mp); Dir = open_root_dir(argv[optind][0], O_RDWR, NULL); if (!Dir) { fprintf(stderr,"%s: Cannot initialize drive\n", argv[0]); exit(1); } Fs = (Fs_t *)GetFs(Dir); in_len = Fs->cluster_size * Fs->sector_size; in_buf = malloc(in_len); if(!in_buf) { printOom(); ret = 1; goto exit_0; } if(writeMode) { int i; pat_buf=malloc(in_len * N_PATTERN); if(!pat_buf) { printOom(); ret = 1; goto exit_0; } srandom(time(NULL)); for(i=0; i < in_len * N_PATTERN; i++) { pat_buf[i] = random(); } } for(i=0; i < Fs->clus_start; i++ ){ ret = READS(Fs->Next, in_buf, sectorsToBytes((Stream_t*)Fs, i), Fs->sector_size); if( ret < 0 ){ perror("early error"); goto exit_0; } if(ret < (signed int) Fs->sector_size){ fprintf(stderr,"end of file in file_read\n"); ret = 1; goto exit_0; } } ret = 0; badClus = Fs->last_fat + 1; if(startSector < 2) startSector = 2; if(endSector > Fs->num_clus + 2 || endSector <= 0) endSector = Fs->num_clus + 2; if(filename) { char line[80]; FILE *f = fopen(filename, "r"); if(f == NULL) { fprintf(stderr, "Could not open %s (%s)\n", filename, strerror(errno)); ret = 1; goto exit_0; } while(fgets(line, sizeof(line), f)) { char *ptr = line + strspn(line, " \t"); long offset = strtoul(ptr, 0, 0); if(sectorMode) offset = (offset-Fs->clus_start)/Fs->cluster_size + 2; if(offset < 2) { fprintf(stderr, "Sector before start\n"); } else if(offset >= Fs->num_clus) { fprintf(stderr, "Sector beyond end\n"); } else { mark(Fs, offset, badClus); ret = 1; } } } else { Stream_t *dev; dev = Fs->Next; if(dev->Next) dev = dev->Next; in_len = Fs->cluster_size * Fs->sector_size; if(writeMode) { /* Write pattern */ for(i=startSector; i< endSector; i++){ if(got_signal) break; progress(i, Fs->num_clus); ret |= scan(Fs, dev, i, badClus, pat_buf + in_len * (i % N_PATTERN), 1); } /* Flush cache, so that we are sure we read the data back from disk, rather than from the cache */ if(!got_signal) DISCARD(dev); /* Read data back, and compare to pattern */ for(i=startSector; i< endSector; i++){ if(got_signal) break; progress(i, Fs->num_clus); ret |= scan(Fs, dev, i, badClus, pat_buf + in_len * (i % N_PATTERN), 0); } } else { for(i=startSector; i< endSector; i++){ if(got_signal) break; progress(i, Fs->num_clus); ret |= scan(Fs, dev, i, badClus, NULL, 0); } } } exit_0: FREE(&Dir); exit(ret); }