Implemented prototype for solving writing records across block boundaries problem

This commit is contained in:
Mario Danic 2007-02-15 03:52:42 +00:00
parent d8a96b00c5
commit 6defb724c4
3 changed files with 51 additions and 21 deletions

View File

@ -1,2 +1,3 @@
Joe Neeman
Philippe Rouquier
David Mohr

View File

@ -7,6 +7,7 @@
#include <time.h>
#include <assert.h>
#include <err.h>
#include <stdarg.h>
#include "ecma119.h"
#include "ecma119_tree.h"
@ -27,8 +28,6 @@ bs_get_size(struct burn_source *bs);
static void
bs_free_data(struct burn_source *bs);
typedef void (*write_fn)(struct ecma119_write_target*, uint8_t*);
/* return true if the given state is only required for Joliet volumes */
static int
is_joliet_state(enum ecma119_write_state);
@ -42,15 +41,15 @@ write_data_chunk(struct ecma119_write_target *t, uint8_t *buf);
/* writing functions. All these functions assume the buf is large enough */
static void
write_pri_vol_desc(struct ecma119_write_target *t, uint8_t *buf);
write_pri_vol_desc(struct ecma119_write_target *t, uint8_t *buf, va_list params);
static void
write_vol_desc_terminator(struct ecma119_write_target *t, uint8_t *buf);
write_vol_desc_terminator(struct ecma119_write_target *t, uint8_t *buf, va_list params);
static void
write_path_table(struct ecma119_write_target *t, int l_type, uint8_t *buf);
static void
write_l_path_table(struct ecma119_write_target *t, uint8_t *buf);
write_l_path_table(struct ecma119_write_target *t, uint8_t *buf, va_list params);
static void
write_m_path_table(struct ecma119_write_target *t, uint8_t *buf);
write_m_path_table(struct ecma119_write_target *t, uint8_t *buf, va_list params);
static void
write_one_dir_record(struct ecma119_write_target *t,
struct ecma119_tree_node *dir,
@ -61,7 +60,7 @@ write_one_dir(struct ecma119_write_target *t,
struct ecma119_tree_node *dir,
uint8_t *buf);
static void
write_dirs(struct ecma119_write_target *t, uint8_t *buf);
write_dirs(struct ecma119_write_target *t, uint8_t *buf, va_list params);
/* wrapper functions for writing */
static void wr_system_area(struct ecma119_write_target*, uint8_t*);
@ -72,7 +71,7 @@ static void wr_m_path_table(struct ecma119_write_target*, uint8_t*);
static void wr_dir_records(struct ecma119_write_target*, uint8_t*);
static void wr_files(struct ecma119_write_target*, uint8_t*);
static const write_fn writers[] =
static const write_fn_wrap writers[] =
{
NULL,
wr_system_area,
@ -391,7 +390,23 @@ wr_m_path_table(struct ecma119_write_target *t, uint8_t *buf)
static void
wr_dir_records(struct ecma119_write_target *t, uint8_t *buf)
{
ecma119_start_chunking(t, write_dirs, t->total_dir_size, buf);
int i;
int j;
size_t size = 0;
size_t dir_size;
struct ecma119_tree_node *dir;
for (i = j = 0; j < t->dirlist_len; j++) {
dir = t->dirlist[j];
dir_size = dir->dir.len + dir->dir.CE_len;
if (size + dir_size > t->block_size) {
/* we are exceeding a logical block now,
* so write all the directory records so far */
ecma119_start_chunking(t, write_dirs, size, buf, i, j-1);
i = j;
size = 0;
}
size += dir_size;
}
}
static void
@ -427,7 +442,7 @@ wr_files(struct ecma119_write_target *t, uint8_t *buf)
}
static void
write_pri_vol_desc(struct ecma119_write_target *t, uint8_t *buf)
write_pri_vol_desc(struct ecma119_write_target *t, uint8_t *buf, va_list params)
{
struct ecma119_pri_vol_desc *vol = (struct ecma119_pri_vol_desc*)buf;
struct iso_volume *volume = t->volset->volume[t->volnum];
@ -469,7 +484,7 @@ write_pri_vol_desc(struct ecma119_write_target *t, uint8_t *buf)
}
static void
write_vol_desc_terminator(struct ecma119_write_target *t, uint8_t *buf)
write_vol_desc_terminator(struct ecma119_write_target *t, uint8_t *buf, va_list params)
{
struct ecma119_vol_desc_terminator *vol =
(struct ecma119_vol_desc_terminator*) buf;
@ -507,13 +522,13 @@ write_path_table(struct ecma119_write_target *t, int l_type, uint8_t *buf)
}
static void
write_l_path_table(struct ecma119_write_target *t, uint8_t *buf)
write_l_path_table(struct ecma119_write_target *t, uint8_t *buf, va_list params)
{
write_path_table(t, 1, buf);
}
static void
write_m_path_table(struct ecma119_write_target *t, uint8_t *buf)
write_m_path_table(struct ecma119_write_target *t, uint8_t *buf, va_list params)
{
write_path_table(t, 0, buf);
}
@ -597,14 +612,19 @@ write_one_dir(struct ecma119_write_target *t,
}
static void
write_dirs(struct ecma119_write_target *t, uint8_t *buf)
write_dirs(struct ecma119_write_target *t, uint8_t *buf, va_list params)
{
size_t i;
int i,start,end;
struct ecma119_tree_node *dir;
for (i = 0; i < t->dirlist_len; i++) {
start = va_arg(params, int);
end = va_arg(params, int);
assert(start >= 0);
assert(end < t->dirlist_len);
for (i = start; i < end; i++) {
dir = t->dirlist[i];
write_one_dir(t, dir, buf);
buf += round_up(dir->dir.len + dir->dir.CE_len, t->block_size);
buf += dir->dir.len + dir->dir.CE_len;
}
}
@ -612,9 +632,13 @@ void
ecma119_start_chunking(struct ecma119_write_target *t,
write_fn writer,
off_t data_size,
uint8_t *buf)
uint8_t *buf,
...)
{
va_list params;
va_start(params, buf);
if (data_size != t->state_data_size) {
/* FIXME: are we sure that roundup works as expected? */
data_size = round_up(data_size, t->block_size);
t->state_data = realloc(t->state_data, data_size);
t->state_data_size = data_size;
@ -622,8 +646,9 @@ ecma119_start_chunking(struct ecma119_write_target *t,
memset(t->state_data, 0, t->state_data_size);
t->state_data_off = 0;
t->state_data_valid = 1;
writer(t, t->state_data);
writer(t, t->state_data, params);
write_data_chunk(t, buf);
va_end(params);
}
static void

View File

@ -258,10 +258,14 @@ struct ecma119_path_table_record
* rather than block-by-block. This creates a buffer of size \p size, passes
* it to the given writer, then hands out block-sized chunks.
*/
typedef void (*write_fn)(struct ecma119_write_target*, uint8_t*, va_list);
typedef void (*write_fn_wrap)(struct ecma119_write_target*, uint8_t*);
void
ecma119_start_chunking(struct ecma119_write_target *t,
void (*)(struct ecma119_write_target*, uint8_t*),
write_fn writer,
off_t size,
uint8_t *buf);
uint8_t *buf,
...);
#endif /* LIBISO_ECMA119_H */