source: mainline/uspace/lib/block/block.h@ c1f26834

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since c1f26834 was 3d35386, checked in by Maurizio Lombardi <m.lombardi85@…>, 11 years ago

libblock: limit the number of retries if we fail to write a block to disk.

The original behaviour is to continously retry to write a block until the
operation succeeds, this will cause the system to enter an infinite loop
if the underlying device is unable to satisfy the request.

This patch introduces an upper limit to the number of retries and discards
the block if the limit is reached.
It also fixes a bug in the block_get() function that allows the user to
try to read a block beyond the end of the device.

  • Property mode set to 100644
File size: 4.2 KB
RevLine 
[fc840d9]1/*
2 * Copyright (c) 2008 Jakub Jermar
[15f3c3f]3 * Copyright (c) 2008 Martin Decky
4 * Copyright (c) 2011 Martin Sucha
[fc840d9]5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 *
11 * - Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * - Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
16 * - The name of the author may not be used to endorse or promote products
17 * derived from this software without specific prior written permission.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
20 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
21 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
22 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
23 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
24 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
28 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 */
30
[b7adc22]31/** @addtogroup libblock
[fc840d9]32 * @{
[b7adc22]33 */
[fc840d9]34/**
35 * @file
36 */
37
38#ifndef LIBBLOCK_LIBBLOCK_H_
[1e4cada]39#define LIBBLOCK_LIBBLOCK_H_
[fc840d9]40
41#include <stdint.h>
[79ae36dd]42#include <async.h>
[1e4cada]43#include <fibril_synch.h>
[d9c8c81]44#include <adt/hash_table.h>
45#include <adt/list.h>
[b7adc22]46#include <loc.h>
[fc840d9]47
[1d8cdb1]48/*
49 * Flags that can be used with block_get().
50 */
51
[b7adc22]52/**
[1d8cdb1]53 * This macro is a symbolic value for situations where no special flags are
54 * needed.
55 */
56#define BLOCK_FLAGS_NONE 0
57
58/**
59 * When the client of block_get() intends to overwrite the current contents of
60 * the block, this flag is used to avoid the unnecessary read.
61 */
62#define BLOCK_FLAGS_NOREAD 1
63
[fc840d9]64typedef struct block {
[4e1b57d]65 /** Mutex protecting the reference count. */
66 fibril_mutex_t lock;
[5cf723b]67 /** Number of references to the block_t structure. */
68 unsigned refcnt;
69 /** If true, the block needs to be written back to the block device. */
[fc840d9]70 bool dirty;
[cd688d9]71 /** If true, the blcok does not contain valid data. */
72 bool toxic;
[5cf723b]73 /** Readers / Writer lock protecting the contents of the block. */
[4e1b57d]74 fibril_rwlock_t contents_lock;
[15f3c3f]75 /** Service ID of service providing the block device. */
76 service_id_t service_id;
[f092718]77 /** Logical block address */
[a6ba0c9]78 aoff64_t lba;
[f092718]79 /** Physical block address */
80 aoff64_t pba;
[5cf723b]81 /** Size of the block. */
82 size_t size;
[3d35386]83 /** Number of write failures. */
84 int write_failures;
[5cf723b]85 /** Link for placing the block into the free block list. */
86 link_t free_link;
87 /** Link for placing the block into the block hash table. */
[062d900]88 ht_link_t hash_link;
[5cf723b]89 /** Buffer with the block data. */
90 void *data;
[fc840d9]91} block_t;
92
[1fbe064b]93/** Caching mode */
94enum cache_mode {
95 /** Write-Through */
96 CACHE_MODE_WT,
97 /** Write-Back */
98 CACHE_MODE_WB
99};
100
[08cba4b]101typedef struct {
102 uint16_t size;
103 uint8_t first_session;
104 uint8_t last_session;
105
106 uint8_t res0;
107 uint8_t adr_ctrl;
108 uint8_t first_track;
109 uint8_t res1;
110
111 uint32_t first_lba;
112} __attribute__((packed)) toc_block_t;
113
[15f3c3f]114extern int block_init(exch_mgmt_t, service_id_t, size_t);
115extern void block_fini(service_id_t);
[6284978]116
[15f3c3f]117extern int block_bb_read(service_id_t, aoff64_t);
118extern void *block_bb_get(service_id_t);
[fc840d9]119
[15f3c3f]120extern int block_cache_init(service_id_t, size_t, unsigned, enum cache_mode);
121extern int block_cache_fini(service_id_t);
[f1ba5d6]122
[15f3c3f]123extern int block_get(block_t **, service_id_t, aoff64_t, int);
[c91f2d1b]124extern int block_put(block_t *);
[fc840d9]125
[4802dd7]126extern int block_seqread(service_id_t, void *, size_t *, size_t *, aoff64_t *,
127 void *, size_t);
[fc840d9]128
[15f3c3f]129extern int block_get_bsize(service_id_t, size_t *);
130extern int block_get_nblocks(service_id_t, aoff64_t *);
[08cba4b]131extern toc_block_t *block_get_toc(service_id_t, uint8_t);
[15f3c3f]132extern int block_read_direct(service_id_t, aoff64_t, size_t, void *);
133extern int block_read_bytes_direct(service_id_t, aoff64_t, size_t, void *);
134extern int block_write_direct(service_id_t, aoff64_t, size_t, const void *);
[00b1d20e]135
[fc840d9]136#endif
137
138/** @}
139 */
Note: See TracBrowser for help on using the repository browser.