]> git.sur5r.net Git - bacula/bacula/blob - bacula/src/stored/block_util.c
11f3cf27ec00389fc8c17c15382630f8d6b7becb
[bacula/bacula] / bacula / src / stored / block_util.c
1 /*
2    Bacula(R) - The Network Backup Solution
3
4    Copyright (C) 2000-2015 Kern Sibbald
5    Copyright (C) 2001-2014 Free Software Foundation Europe e.V.
6
7    The original author of Bacula is Kern Sibbald, with contributions
8    from many others, a complete list can be found in the file AUTHORS.
9
10    You may use this file and others of this release according to the
11    license defined in the LICENSE file, which includes the Affero General
12    Public License, v3.0 ("AGPLv3") and some additional permissions and
13    terms pursuant to its AGPLv3 Section 7.
14
15    This notice must be preserved when any source code is 
16    conveyed and/or propagated.
17
18    Bacula(R) is a registered trademark of Kern Sibbald.
19 */
20 /*
21  *
22  *   block_util.c -- tape block utility functions
23  *
24  *              Kern Sibbald, split from block.c March MMXII
25  *
26  */
27
28
29 #include "bacula.h"
30 #include "stored.h"
31
32 static const int dbgel = 160;
33
34 #ifdef DEBUG_BLOCK_CHECKSUM
35 static const bool debug_block_checksum = true;
36 #else
37 static const bool debug_block_checksum = false;
38 #endif
39
40 #ifdef NO_TAPE_WRITE_TEST
41 static const bool no_tape_write_test = true;
42 #else
43 static const bool no_tape_write_test = false;
44 #endif
45
46 /*
47  * Dump the block header, then walk through
48  * the block printing out the record headers.
49  */
50 void dump_block(DEV_BLOCK *b, const char *msg)
51 {
52    ser_declare;
53    char *p;
54    char Id[BLKHDR_ID_LENGTH+1];
55    uint32_t CheckSum, BlockCheckSum;
56    uint32_t block_len, reclen;
57    uint32_t BlockNumber;
58    uint32_t VolSessionId, VolSessionTime, data_len;
59    int32_t  FileIndex;
60    int32_t  Stream;
61    int bhl, rhl;
62    char buf1[100], buf2[100];
63
64    if ((debug_level & ~DT_ALL) < 250) {
65       return;
66    }
67    unser_begin(b->buf, BLKHDR1_LENGTH);
68    unser_uint32(CheckSum);
69    unser_uint32(block_len);
70    unser_uint32(BlockNumber);
71    unser_bytes(Id, BLKHDR_ID_LENGTH);
72    ASSERT(unser_length(b->buf) == BLKHDR1_LENGTH);
73    Id[BLKHDR_ID_LENGTH] = 0;
74    if (Id[3] == '2') {
75       unser_uint32(VolSessionId);
76       unser_uint32(VolSessionTime);
77       bhl = BLKHDR2_LENGTH;
78       rhl = RECHDR2_LENGTH;
79    } else {
80       VolSessionId = VolSessionTime = 0;
81       bhl = BLKHDR1_LENGTH;
82       rhl = RECHDR1_LENGTH;
83    }
84
85    if (block_len > 4000000 || block_len < BLKHDR_CS_LENGTH) {
86       Dmsg4(20, "!!!Dump block %s %p blocksize too %s %lu\n",
87             msg, b,
88             (block_len < BLKHDR_CS_LENGTH)?"small":"big",
89             block_len);
90       return;
91    }
92
93    BlockCheckSum = bcrc32((uint8_t *)b->buf+BLKHDR_CS_LENGTH,
94                          block_len-BLKHDR_CS_LENGTH);
95    Pmsg6(000, _("Dump block %s %p: size=%d BlkNum=%d\n"
96 "               Hdrcksum=%x cksum=%x\n"),
97       msg, b, block_len, BlockNumber, CheckSum, BlockCheckSum);
98    p = b->buf + bhl;
99    while (p < b->bufp) {
100       unser_begin(p, WRITE_RECHDR_LENGTH);
101       if (rhl == RECHDR1_LENGTH) {
102          unser_uint32(VolSessionId);
103          unser_uint32(VolSessionTime);
104       }
105       unser_int32(FileIndex);
106       unser_int32(Stream);
107       unser_uint32(data_len);
108       reclen = 0;
109       p += data_len + rhl;
110       Pmsg6(000, _("   Rec: VId=%u VT=%u FI=%s Strm=%s len=%d reclen=%d\n"),
111            VolSessionId, VolSessionTime, FI_to_ascii(buf1, FileIndex),
112            stream_to_ascii(buf2, Stream, FileIndex), data_len, reclen);
113   }
114 }
115
116 /*
117  * Create a new block structure.
118  * We pass device so that the block can inherit the
119  * min and max block sizes.
120  */
121 DEV_BLOCK *new_block(DEVICE *dev)
122 {
123    DEV_BLOCK *block = (DEV_BLOCK *)get_memory(sizeof(DEV_BLOCK));
124    int len;
125
126    memset(block, 0, sizeof(DEV_BLOCK));
127
128    /* If the user has specified a max_block_size, use it as the default */
129    if (dev->max_block_size == 0) {
130       len = DEFAULT_BLOCK_SIZE;
131    } else {
132       len = dev->max_block_size;
133    }
134    block->dev = dev;
135    /*
136     * Round to multiple of block size + ensure that
137     * the data length is a multiple of the block size
138     */
139    block->buf_len = len;
140    block->buf = get_memory(block->buf_len);
141    block->rechdr_items = 0;
142    empty_block(block);
143    block->BlockVer = BLOCK_VER;       /* default write version */
144    Dmsg2(150, "New block len=%d block=%p\n", len, block);
145    return block;
146 }
147
148
149 /*
150  * Duplicate an existing block (eblock)
151  */
152 DEV_BLOCK *dup_block(DEV_BLOCK *eblock)
153 {
154    DEV_BLOCK *block = (DEV_BLOCK *)get_memory(sizeof(DEV_BLOCK));
155    int buf_len = sizeof_pool_memory(eblock->buf);
156
157    memcpy(block, eblock, sizeof(DEV_BLOCK));
158    block->buf = get_memory(buf_len);
159    memcpy(block->buf, eblock->buf, buf_len);
160    return block;
161 }
162
163
164 /*
165  * Only the first block checksum error was reported.
166  *   If there are more, report it now.
167  */
168 void print_block_read_errors(JCR *jcr, DEV_BLOCK *block)
169 {
170    if (block->read_errors > 1) {
171       Jmsg(jcr, M_ERROR, 0, _("%d block read errors not printed.\n"),
172          block->read_errors);
173    }
174 }
175
176
177 void DCR::free_blocks()
178 {
179    if (block) {
180       free_block(block);
181    }
182 }
183
184 /*
185  * Free block
186  */
187 void free_block(DEV_BLOCK *block)
188 {
189    if (block && block->buf) {
190       Dmsg1(999, "free_block buffer %x\n", block->buf);
191       free_memory(block->buf);
192       Dmsg1(999, "free_block block %x\n", block);
193       free_memory((POOLMEM *)block);
194    }
195 }
196
197 bool is_block_empty(DEV_BLOCK *block)
198 {
199    return block->binbuf <= WRITE_BLKHDR_LENGTH;
200 }
201
202 /* Empty the block -- for writing */
203 void empty_block(DEV_BLOCK *block)
204 {
205    block->binbuf = WRITE_BLKHDR_LENGTH;
206    Dmsg3(200, "empty len=%d block=%p set binbuf=%d\n",
207          block->buf_len, block, block->binbuf);
208    block->bufp = block->buf + block->binbuf;
209    block->buf[0] = 0;        /* clear for debugging */
210    block->bufp[0] = 0;       /* clear for debugging */
211    block->read_len = 0;
212    block->write_failed = false;
213    block->block_read = false;
214    block->needs_write = false;
215    block->FirstIndex = block->LastIndex = 0;
216 }
217
218 /*
219  * Create block header just before write. The space
220  * in the buffer should have already been reserved by
221  * init_block.
222  */
223 uint32_t ser_block_header(DEV_BLOCK *block, bool do_checksum)
224 {
225    ser_declare;
226    uint32_t block_len = block->binbuf;
227
228    block->CheckSum = 0;
229    Dmsg1(160, "block_header: block_len=%d\n", block_len);
230    ser_begin(block->buf, BLKHDR2_LENGTH);
231    ser_uint32(block->CheckSum);
232    ser_uint32(block_len);
233    ser_uint32(block->BlockNumber);
234    ser_bytes(WRITE_BLKHDR_ID, BLKHDR_ID_LENGTH);
235    if (BLOCK_VER >= 2) {
236       ser_uint32(block->VolSessionId);
237       ser_uint32(block->VolSessionTime);
238    }
239
240    /* Checksum whole block except for the checksum */
241    if (do_checksum) {
242       block->CheckSum = bcrc32((uint8_t *)block->buf+BLKHDR_CS_LENGTH,
243                     block_len-BLKHDR_CS_LENGTH);
244    }
245    Dmsg1(160, "ser_block_header: checksum=%x\n", block->CheckSum);
246    ser_begin(block->buf, BLKHDR2_LENGTH);
247    ser_uint32(block->CheckSum);    /* now add checksum to block header */
248    return block->CheckSum;
249 }
250
251 /*
252  * Unserialize the block header for reading block.
253  *  This includes setting all the buffer pointers correctly.
254  *
255  *  Returns: false on failure (not a block)
256  *           true  on success
257  */
258 bool unser_block_header(JCR *jcr, DEVICE *dev, DEV_BLOCK *block)
259 {
260    ser_declare;
261    char Id[BLKHDR_ID_LENGTH+1];
262    uint32_t BlockCheckSum;
263    uint32_t block_len;
264    uint32_t block_end;
265    uint32_t BlockNumber;
266    int bhl;
267
268    if (block->no_header) {
269       return true;
270    }
271    unser_begin(block->buf, BLKHDR_LENGTH);
272    unser_uint32(block->CheckSum);
273    unser_uint32(block_len);
274    unser_uint32(BlockNumber);
275    unser_bytes(Id, BLKHDR_ID_LENGTH);
276    ASSERT(unser_length(block->buf) == BLKHDR1_LENGTH);
277    Id[BLKHDR_ID_LENGTH] = 0;
278
279    if (Id[3] == '1') {
280       bhl = BLKHDR1_LENGTH;
281       block->BlockVer = 1;
282       block->bufp = block->buf + bhl;
283       //Dmsg3(100, "Block=%p buf=%p bufp=%p\n", block, block->buf, block->bufp);
284       if (strncmp(Id, BLKHDR1_ID, BLKHDR_ID_LENGTH) != 0) {
285          dev->dev_errno = EIO;
286          Mmsg4(dev->errmsg, _("Volume data error at %u:%u! Wanted ID: \"%s\", got \"%s\". Buffer discarded.\n"),
287             dev->file, dev->block_num, BLKHDR1_ID, Id);
288          if (block->read_errors == 0 || verbose >= 2) {
289             Jmsg(jcr, M_ERROR, 0, "%s", dev->errmsg);
290          }
291          block->read_errors++;
292          return false;
293       }
294    } else if (Id[3] == '2') {
295       unser_uint32(block->VolSessionId);
296       unser_uint32(block->VolSessionTime);
297       bhl = BLKHDR2_LENGTH;
298       block->BlockVer = 2;
299       block->bufp = block->buf + bhl;
300       if (strncmp(Id, BLKHDR2_ID, BLKHDR_ID_LENGTH) != 0) {
301          dev->dev_errno = EIO;
302          Mmsg4(dev->errmsg, _("Volume data error at %u:%u! Wanted ID: \"%s\", got \"%s\". Buffer discarded.\n"),
303             dev->file, dev->block_num, BLKHDR2_ID, Id);
304          if (block->read_errors == 0 || verbose >= 2) {
305             Jmsg(jcr, M_ERROR, 0, "%s", dev->errmsg);
306          }
307          block->read_errors++;
308          return false;
309       }
310    } else {
311       dev->dev_errno = EIO;
312       Mmsg4(dev->errmsg, _("Volume data error at %u:%u! Wanted ID: \"%s\", got \"%s\". Buffer discarded.\n"),
313           dev->file, dev->block_num, BLKHDR2_ID, Id);
314       Dmsg1(50, "%s", dev->errmsg);
315       if (block->read_errors == 0 || verbose >= 2) {
316          Jmsg(jcr, M_ERROR, 0, "%s", dev->errmsg);
317       }
318       block->read_errors++;
319       unser_uint32(block->VolSessionId);
320       unser_uint32(block->VolSessionTime);
321       return false;
322    }
323
324    /* Sanity check */
325    if (block_len > MAX_BLOCK_LENGTH) {
326       dev->dev_errno = EIO;
327       Mmsg3(dev->errmsg,  _("Volume data error at %u:%u! Block length %u is insane (too large), probably due to a bad archive.\n"),
328          dev->file, dev->block_num, block_len);
329       if (block->read_errors == 0 || verbose >= 2) {
330          Jmsg(jcr, M_ERROR, 0, "%s", dev->errmsg);
331       }
332       block->read_errors++;
333       return false;
334    }
335
336    Dmsg1(390, "unser_block_header block_len=%d\n", block_len);
337    /* Find end of block or end of buffer whichever is smaller */
338    if (block_len > block->read_len) {
339       block_end = block->read_len;
340    } else {
341       block_end = block_len;
342    }
343    block->binbuf = block_end - bhl;
344    Dmsg2(200, "set block=%p binbuf=%d\n", block, block->binbuf);
345    block->block_len = block_len;
346    block->BlockNumber = BlockNumber;
347    Dmsg3(390, "Read binbuf = %d %d block_len=%d\n", block->binbuf,
348       bhl, block_len);
349    if (block_len <= block->read_len && dev->do_checksum()) {
350       BlockCheckSum = bcrc32((uint8_t *)block->buf+BLKHDR_CS_LENGTH,
351                          block_len-BLKHDR_CS_LENGTH);
352       if (BlockCheckSum != block->CheckSum) {
353          dev->dev_errno = EIO;
354          Mmsg6(dev->errmsg, _("Volume data error at %u:%u!\n"
355             "Block checksum mismatch in block=%u len=%d: calc=%x blk=%x\n"),
356             dev->file, dev->block_num, (unsigned)BlockNumber,
357             block_len, BlockCheckSum, block->CheckSum);
358          if (block->read_errors == 0 || verbose >= 2) {
359             Jmsg(jcr, M_ERROR, 0, "%s", dev->errmsg);
360             dump_block(block, "with checksum error");
361          }
362          block->read_errors++;
363          if (!forge_on) {
364             return false;
365          }
366       }
367    }
368    return true;
369 }
370
371 /*
372  * Calculate how many bytes to write and then clear to end
373  *  of block.
374  */
375 uint32_t get_len_and_clear_block(DEV_BLOCK *block, DEVICE *dev, uint32_t &pad)
376 {
377    uint32_t wlen;
378    /*
379     * Clear to the end of the buffer if it is not full,
380     *  and on tape devices, apply min and fixed blocking.
381     */
382    wlen = block->binbuf;
383    if (wlen != block->buf_len) {
384       Dmsg2(250, "binbuf=%d buf_len=%d\n", block->binbuf, block->buf_len);
385
386       /* Adjust write size to min/max for tapes only */
387       if (dev->is_tape()) {
388          /* check for fixed block size */
389          if (dev->min_block_size == dev->max_block_size) {
390             wlen = block->buf_len;    /* fixed block size already rounded */
391          /* Check for min block size */
392          } else if (wlen < dev->min_block_size) {
393             wlen =  ((dev->min_block_size + TAPE_BSIZE - 1) / TAPE_BSIZE) * TAPE_BSIZE;
394          /* Ensure size is rounded */
395          } else {
396             wlen = ((wlen + TAPE_BSIZE - 1) / TAPE_BSIZE) * TAPE_BSIZE;
397          }
398       }
399       ASSERT(wlen <= block->buf_len);
400       /* Clear from end of data to end of block */
401       if (wlen-block->binbuf > 0) {
402          memset(block->bufp, 0, wlen-block->binbuf); /* clear garbage */
403       }
404       pad = wlen - block->binbuf;        /* padding or zeros written */
405       Dmsg4(150, "Zero end blk: cleared=%d buf_len=%d wlen=%d binbuf=%d\n",
406          pad, block->buf_len, wlen, block->binbuf);
407    } else {
408       pad = 0;
409    }
410
411    return wlen;              /* bytes to write */
412 }
413
414 /*
415  * Determine if user defined volume size has been
416  *  reached, and if so, return true, otherwise
417  *  return false.
418  */
419 bool user_volume_size_reached(DCR *dcr, bool quiet)
420 {
421    bool hit_max1, hit_max2;
422    uint64_t size, max_size;
423    DEVICE *dev = dcr->dev;
424    char ed1[50];
425    bool rtn = false;
426
427    Enter(dbgel);
428    size = dev->VolCatInfo.VolCatBytes + dcr->block->binbuf;
429    /* Limit maximum Volume size to value specified by user */
430    hit_max1 = (dev->max_volume_size > 0) && (size >= dev->max_volume_size);
431    hit_max2 = (dev->VolCatInfo.VolCatMaxBytes > 0) &&
432        (size >= dev->VolCatInfo.VolCatMaxBytes);
433    if (hit_max1) {
434       max_size = dev->max_volume_size;
435    } else {
436       max_size = dev->VolCatInfo.VolCatMaxBytes;
437    }
438    if (hit_max1 || hit_max2) {
439       if (!quiet) {
440          Jmsg(dcr->jcr, M_INFO, 0, _("User defined maximum volume size %s will be exceeded on device %s.\n"
441             "   Marking Volume \"%s\" as Full.\n"),
442             edit_uint64_with_commas(max_size, ed1),  dev->print_name(),
443             dev->getVolCatName());
444       }
445       Dmsg4(100, "Maximum volume size %s exceeded Vol=%s device=%s.\n"
446          "Marking Volume \"%s\" as Full.\n",
447          edit_uint64_with_commas(max_size, ed1), dev->getVolCatName(),
448          dev->print_name(), dev->getVolCatName());
449       rtn = true;
450    }
451    Dmsg1(dbgel, "Return from user_volume_size_reached=%d\n", rtn);
452    Leave(dbgel);
453    return rtn;
454 }
455
456
457 void reread_last_block(DCR *dcr)
458 {
459 #define CHECK_LAST_BLOCK
460 #ifdef  CHECK_LAST_BLOCK
461    bool ok = true;
462    DEVICE *dev = dcr->dev;
463    JCR *jcr = dcr->jcr;
464    DEV_BLOCK *block = dcr->block;
465    /*
466     * If the device is a tape and it supports backspace record,
467     *   we backspace over one or two eof marks depending on
468     *   how many we just wrote, then over the last record,
469     *   then re-read it and verify that the block number is
470     *   correct.
471     */
472    if (dev->is_tape() && dev->has_cap(CAP_BSR)) {
473       /* Now back up over what we wrote and read the last block */
474       if (!dev->bsf(1)) {
475          berrno be;
476          ok = false;
477          Jmsg(jcr, M_ERROR, 0, _("Backspace file at EOT failed. ERR=%s\n"),
478               be.bstrerror(dev->dev_errno));
479       }
480       if (ok && dev->has_cap(CAP_TWOEOF) && !dev->bsf(1)) {
481          berrno be;
482          ok = false;
483          Jmsg(jcr, M_ERROR, 0, _("Backspace file at EOT failed. ERR=%s\n"),
484               be.bstrerror(dev->dev_errno));
485       }
486       /* Backspace over record */
487       if (ok && !dev->bsr(1)) {
488          berrno be;
489          ok = false;
490          Jmsg(jcr, M_ERROR, 0, _("Backspace record at EOT failed. ERR=%s\n"),
491               be.bstrerror(dev->dev_errno));
492          /*
493           *  On FreeBSD systems, if the user got here, it is likely that his/her
494           *    tape drive is "frozen".  The correct thing to do is a
495           *    rewind(), but if we do that, higher levels in cleaning up, will
496           *    most likely write the EOS record over the beginning of the
497           *    tape.  The rewind *is* done later in mount.c when another
498           *    tape is requested. Note, the clrerror() call in bsr()
499           *    calls ioctl(MTCERRSTAT), which *should* fix the problem.
500           */
501       }
502       if (ok) {
503          DEV_BLOCK *lblock = new_block(dev);
504          /* Note, this can destroy dev->errmsg */
505          dcr->block = lblock;
506          if (!dcr->read_block_from_dev(NO_BLOCK_NUMBER_CHECK)) {
507             Jmsg(jcr, M_ERROR, 0, _("Re-read last block at EOT failed. ERR=%s"),
508                  dev->errmsg);
509          } else {
510             /*
511              * If we wrote block and the block numbers don't agree
512              *  we have a possible problem.
513              */
514             if (lblock->BlockNumber != dev->LastBlock) {
515                 if (dev->LastBlock > (lblock->BlockNumber + 1)) {
516                    Jmsg(jcr, M_FATAL, 0, _(
517 "Re-read of last block: block numbers differ by more than one.\n"
518 "Probable tape misconfiguration and data loss. Read block=%u Want block=%u.\n"),
519                        lblock->BlockNumber, dev->LastBlock);
520                  } else {
521                    Jmsg(jcr, M_ERROR, 0, _(
522 "Re-read of last block OK, but block numbers differ. Read block=%u Want block=%u.\n"),
523                        lblock->BlockNumber, dev->LastBlock);
524                  }
525             } else {
526                Jmsg(jcr, M_INFO, 0, _("Re-read of last block succeeded.\n"));
527             }
528          }
529          free_block(lblock);
530          dcr->block = block;
531       }
532    }
533 #endif
534 }
535
536 /*
537  * If this routine is called, we do our bookkeeping and
538  *   then assure that the volume will not be written any
539  *   more.
540  */
541 bool terminate_writing_volume(DCR *dcr)
542 {
543    DEVICE *dev = dcr->dev;
544    bool ok = true;
545
546    Enter(dbgel);
547
548    if (dev->is_ateot()) {
549       return ok;          /* already been here return now */
550    }
551
552    /* Create a JobMedia record to indicated end of medium */
553    dev->VolCatInfo.VolCatFiles = dev->get_file();
554    if (!dir_create_jobmedia_record(dcr)) {
555       Dmsg0(50, "Error from create JobMedia\n");
556       dev->dev_errno = EIO;
557         Mmsg2(dev->errmsg, _("Could not create JobMedia record for Volume=\"%s\" Job=%s\n"),
558             dev->getVolCatName(), dcr->jcr->Job);
559        Jmsg(dcr->jcr, M_FATAL, 0, "%s", dev->errmsg);
560        ok = false;
561    }
562    flush_jobmedia_queue(dcr->jcr);
563    dcr->block->write_failed = true;
564    if (dev->can_append() && !dev->weof(1)) {     /* end the tape */
565       dev->VolCatInfo.VolCatErrors++;
566       Jmsg(dcr->jcr, M_ERROR, 0, _("Error writing final EOF to tape. This Volume may not be readable.\n"
567            "%s"), dev->errmsg);
568       ok = false;
569       Dmsg0(50, "Error writing final EOF to volume.\n");
570    }
571    if (ok) {
572       ok = write_ansi_ibm_labels(dcr, ANSI_EOV_LABEL, dev->VolHdr.VolumeName);
573    }
574
575    Dmsg2(100, "Set VolCatStatus Full size=%lld vol=%s\n",
576       dev->VolCatInfo.VolCatBytes, dev->VolCatInfo.VolCatName);
577
578    /* If still in append mode mark volume Full */
579    if (bstrcmp(dev->VolCatInfo.VolCatStatus, "Append")) {
580       dev->setVolCatStatus("Full");
581    }
582
583    if (!dir_update_volume_info(dcr, false, true)) {
584       Mmsg(dev->errmsg, _("Error sending Volume info to Director.\n"));
585       ok = false;
586       Dmsg0(50, "Error updating volume info.\n");
587    }
588    Dmsg2(150, "dir_update_volume_info vol=%s to terminate writing -- %s\n",
589       dev->getVolCatName(), ok?"OK":"ERROR");
590
591    dev->notify_newvol_in_attached_dcrs(NULL);
592
593    /* Set new file/block parameters for current dcr */
594    set_new_file_parameters(dcr);
595
596    if (ok && dev->has_cap(CAP_TWOEOF) && dev->can_append() && !dev->weof(1)) {  /* end the tape */
597       dev->VolCatInfo.VolCatErrors++;
598       /* This may not be fatal since we already wrote an EOF */
599       Jmsg(dcr->jcr, M_ERROR, 0, "%s", dev->errmsg);
600       Dmsg0(50, "Writing second EOF failed.\n");
601    }
602
603    dev->set_ateot();                  /* no more writing this tape */
604    Dmsg2(150, "Leave terminate_writing_volume=%s -- %s\n",
605       dev->getVolCatName(), ok?"OK":"ERROR");
606    Leave(dbgel);
607    return ok;
608 }
609
610 /*
611  * If a new volume has been mounted since our last write
612  *   Create a JobMedia record for the previous volume written,
613  *   and set new parameters to write this volume
614  * The same applies for if we are in a new file.
615  */
616 bool check_for_newvol_or_newfile(DCR *dcr)
617 {
618    JCR *jcr = dcr->jcr;
619
620    if (dcr->NewVol || dcr->NewFile) {
621       if (job_canceled(jcr)) {
622          Dmsg0(100, "Canceled\n");
623          return false;
624       }
625       /* Create a jobmedia record for this job */
626       if (!dir_create_jobmedia_record(dcr)) {
627          dcr->dev->dev_errno = EIO;
628          Jmsg2(jcr, M_FATAL, 0, _("Could not create JobMedia record for Volume=\"%s\" Job=%s\n"),
629             dcr->getVolCatName(), jcr->Job);
630          set_new_volume_parameters(dcr);
631          Dmsg0(100, "cannot create media record\n");
632          return false;
633       }
634       if (dcr->NewVol) {
635          flush_jobmedia_queue(jcr);
636          /* Note, setting a new volume also handles any pending new file */
637          set_new_volume_parameters(dcr);
638       } else {
639          set_new_file_parameters(dcr);
640       }
641    }
642    return true;
643 }
644
645 /*
646  * Do bookkeeping when a new file is created on a Volume. This is
647  *  also done for disk files to generate the jobmedia records for
648  *  quick seeking.
649  */
650 bool do_new_file_bookkeeping(DCR *dcr)
651 {
652    DEVICE *dev = dcr->dev;
653    JCR *jcr = dcr->jcr;
654
655    /* Create a JobMedia record so restore can seek */
656    if (!dir_create_jobmedia_record(dcr)) {
657       Dmsg0(40, "Error from create_job_media.\n");
658       dev->dev_errno = EIO;
659       Jmsg2(jcr, M_FATAL, 0, _("Could not create JobMedia record for Volume=\"%s\" Job=%s\n"),
660            dcr->getVolCatName(), jcr->Job);
661       Dmsg0(40, "Call terminate_writing_volume\n");
662       terminate_writing_volume(dcr);
663       dev->dev_errno = EIO;
664       return false;
665    }
666    dev->VolCatInfo.VolCatFiles = dev->get_file();
667    if (!dir_update_volume_info(dcr, false, false)) {
668       Dmsg0(50, "Error from update_vol_info.\n");
669       Dmsg0(40, "Call terminate_writing_volume\n");
670       terminate_writing_volume(dcr);
671       dev->dev_errno = EIO;
672       return false;
673    }
674    Dmsg0(100, "dir_update_volume_info max file size -- OK\n");
675
676    dev->notify_newfile_in_attached_dcrs();
677
678    /* Set new file/block parameters for current dcr */
679    set_new_file_parameters(dcr);
680    return true;
681 }