Fix liberasurecode main routines for new API (take 2)

Signed-off-by: Tushar Gohad <tushar.gohad@intel.com>
This commit is contained in:
Tushar Gohad 2014-07-16 12:58:41 -07:00
parent 1c632ec72c
commit 05e65c3f96
5 changed files with 146 additions and 73 deletions

View File

@ -127,6 +127,9 @@
*/
#undef LT_OBJDIR
/* Define to 1 if your C compiler doesn't accept -c and -o together. */
#undef NO_MINUS_C_MINUS_O
/* Name of package */
#undef PACKAGE

View File

@ -39,7 +39,6 @@ extern "C" {
/* =~=*=~==~=*=~==~=*=~= Supported EC backends =~=*=~==~=*=~==~=*=~==~=*=~== */
/* Supported EC backends */
typedef enum {
EC_BACKEND_NULL = 0,
EC_BACKEND_JERASURE_RS_VAND = 1,
@ -48,11 +47,16 @@ typedef enum {
EC_BACKENDS_MAX,
} ec_backend_id_t;
const char *ec_backend_names[EC_BACKENDS_MAX] =
#ifdef EC_BACKENDS_SUPPORTED
#define EC_BACKENDS_SUPPORTED
/* Supported EC backends */
const char *ec_backend_names[EC_BACKENDS_MAX] = {
"null",
"jerasure_rs_vand",
"jerasure_rs_cauchy",
"flat_xor_hd";
"flat_xor_hd",
};
#endif // EC_BACKENDS_SUPPORTED
/* =~=*=~==~=*=~== EC Arguments - Common and backend-specific =~=*=~==~=*=~== */
@ -82,7 +86,7 @@ struct ec_args {
int inline_chksum; /* embedded fragment checksums (yes/no), type */
int algsig_chksum; /* use algorithmic signature checksums */
}
};
/* =~=*=~==~=*=~== liberasurecode frontend API functions =~=*=~==~=~=*=~==~= */
@ -169,7 +173,8 @@ int liberasurecode_reconstruct_fragment(int desc,
/**
* Determine which fragments are needed to reconstruct some subset
* of missing fragments.
* of missing fragments. Returns a list of lists (as bitmaps)
* of fragments required to reconstruct missing indexes.
*/
int liberasurecode_fragments_needed(int desc,
int *missing_idxs, int *fragments_needed);

View File

@ -25,7 +25,8 @@
#ifndef _ERASURECODE_INTERNAL_H_
#define _ERASURECODE_INTERNAL_H_
#include "erasurecode.h"
#include "list.h"
#include "erasurecode_stdinc.h"
/* ~=*=~===~=*=~==~=*=~==~=*=~= backend infrastructure =~=*=~==~=*=~==~=*=~ */
@ -39,11 +40,13 @@ extern "C" {
#define dl_restrict
#endif
/* ==~=*=~===~=*=~==~=*=~==~=*=~= EC backend args =~==~=*=~==~=*=~===~=*=~== */
/* Arguments passed to the backend */
#define MAX_PRIV_ARGS 4
struct ec_backend_args {
struct ec_args *common_args; /* common args passed in by the user */
void *priv_args[MAX_PRIV_ARGS]; /* used for private backend args */
struct ec_args *uargs; /* common args passed in by the user */
void *pargs[MAX_PRIV_ARGS]; /* used for private backend args */
};
/* =~===~=*=~==~=*=~==~=*=~= backend stub definitions =~=*=~==~=*=~==~=*=~= */
@ -73,13 +76,17 @@ struct ec_backend_op_stubs {
* Backend stub declarations - the stubs translate generic backend args
* to backend specific args and call (*fptr)()
*/
int (*ENCODE)(void *desc, int (*fptr)(),
/** FIXME - not sure if we need both 'desc' and also 'ec_backend_args'
* if we can call directly into xor_codes without 'desc', we can do
* away with desc. will try that in the next rev */
int (*ENCODE)(void *desc, int (*fptr)(), struct ec_backend_args *args,
char **data, char **parity, int blocksize);
int (*DECODE)(void *desc, int (*fptr)(),
int (*DECODE)(void *desc, int (*fptr)(), struct ec_backend_args *args,
char **data, char **parity, int *missing_idxs, int blocksize);
int (*FRAGSNEEDED)(void *desc, int (*fptr)(),
int (*FRAGSNEEDED)(void *desc, int (*fptr)(), struct ec_backend_args *args,
int *missing_idxs, int *fragments_needed);
int (*RECONSTRUCT)(void *desc, int (*fptr)(),
int (*RECONSTRUCT)(void *desc, int (*fptr)(), struct ec_backend_args *args,
char **data, char **parity, int *missing_idxs, int destination_idx,
int blocksize);
};
@ -140,10 +147,10 @@ int liberasurecode_backend_close(ec_backend_t instance);
/* Backend query interface */
/* Name to ID mapping for EC backend */
ec_backend_id_t liberasurecode_backend_lookup_id(const char *name)
ec_backend_id_t liberasurecode_backend_lookup_id(const char *name);
/* Get EC backend by name */
ec_backend_t liberasurecode_backend_lookup_by_name(const char *name)
ec_backend_t liberasurecode_backend_lookup_by_name(const char *name);
/**
* Look up a backend instance by descriptor
@ -151,17 +158,7 @@ ec_backend_t liberasurecode_backend_lookup_by_name(const char *name)
* Returns pointer to a registered liberasurecode instance
* The caller must hold active_instances_rwlock
*/
ec_backend_t liberasurecode_backend_instance_get_by_desc(int desc)
/**
* Lookup backend library function name given stub name
*
* @map - function stub name to library function name map
* @stub - backend stub name
*
* @returns pointer to a string representing backend library function name
*/
const char *lookup_fn_name(struct ec_backend_fnmap *map, const char *stub)
ec_backend_t liberasurecode_backend_instance_get_by_desc(int desc);
/* =~=*=~==~=*=~==~=*=~==~=*=~===~=*=~==~=*=~===~=*=~==~=*=~===~=*=~==~=*=~= */

View File

@ -25,6 +25,8 @@
#include <stdio.h>
#include <stdlib.h>
#include <xor_code.h>
#include "erasurecode.h"
#include "erasurecode_backend.h"
/* Forward declarations */
@ -32,13 +34,15 @@ struct ec_backend_op_stubs flat_xor_hd_ops;
struct ec_backend flat_xor_hd;
static int flat_xor_hd_encode(void *desc, int (*fptr)(),
char **data, char **parity, int blocksize)
struct ec_backend_args *args,
char **data, char **parity, int blocksize)
{
xor_code_t *xor_desc = (xor_code_t *) desc;
xor_desc->encode(xor_desc, data, parity, blocksize);
}
static int flat_xor_hd_decode(void *desc, int (*fptr)(),
struct ec_backend_args *args,
char **data, char **parity, int *missing_idxs,
int blocksize)
{
@ -47,6 +51,7 @@ static int flat_xor_hd_decode(void *desc, int (*fptr)(),
}
static int flat_xor_hd_reconstruct(void *desc, int (*fptr)(),
struct ec_backend_args *args,
char **data, char **parity, int *missing_idxs,
int destination_idx, int blocksize)
{
@ -55,6 +60,7 @@ static int flat_xor_hd_reconstruct(void *desc, int (*fptr)(),
}
static int flat_xor_hd_min_fragments(void *desc, int (*fptr)(),
struct ec_backend_args *args,
int *missing_idxs, int *fragments_needed)
{
xor_code_t *xor_desc = (xor_code_t *) desc;
@ -63,7 +69,10 @@ static int flat_xor_hd_min_fragments(void *desc, int (*fptr)(),
static void * flat_xor_hd_init(struct ec_backend_args *args)
{
void *desc = (void *) init_xor_hd_code(args->k, args->m, args->hd);
int k = args->uargs->k;
int m = args->uargs->m;
int hd = args->uargs->priv_args1.flat_xor_hd_args.hd;
void *desc = (void *) init_xor_hd_code(k, m, hd);
return desc;
}
@ -92,7 +101,7 @@ struct ec_backend_fnmap flat_xor_hd_fn_map[MAX_FNS] = {
};
struct ec_backend_common backend_flat_xor_hd = {
.id = EC_BACKEND_FLAT_XOR_3,
.id = EC_BACKEND_FLAT_XOR_HD,
.name = "flat_xor_hd",
.soname = "libXorcode.so",
.soversion = "1.0",

View File

@ -209,7 +209,7 @@ int liberasurecode_backend_close(ec_backend_t instance)
* @returns liberasurecode instance descriptor (int > 0)
*/
int liberasurecode_instance_create(const char *backend_name,
struct ec_args *args);
struct ec_args *args)
{
int err = 0;
ec_backend_t instance = NULL;
@ -237,7 +237,7 @@ int liberasurecode_instance_create(const char *backend_name,
}
/* Call private init() for the backend */
instance->backend_desc = instance->common.ops->init(args);
instance->backend_desc = instance->common.ops->init(instance->args);
/* Register instance and return a descriptor/instance id */
instance->instance_desc = liberasurecode_backend_instance_register(instance);
@ -278,6 +278,7 @@ int liberasurecode_instance_destroy(int desc)
*
* @returns pointer to a string representing backend library function name
*/
static inline
const char *lookup_fn_name(struct ec_backend_fnmap *map, const char *stub)
{
int i = 0;
@ -293,6 +294,34 @@ const char *lookup_fn_name(struct ec_backend_fnmap *map, const char *stub)
return fn_name;
}
/**
* Look up backend instance by descriptor (int) passed by user and
* find corresponding backend function reference for a given stub
* name ("encode", "decode" etc)
*/
static inline
int liberasurecode_backend_lookup_instance_and_method(
int desc, ec_backend_t *instance,
const char *stub, int (*fptr)())
{
ec_backend_t x = NULL;
const char *fn_name = NULL;
x = liberasurecode_backend_instance_get_by_desc(desc);
if (x == NULL)
return -ENOENT;
fn_name = lookup_fn_name(x->common.fnmap, stub);
/* find the address of the DECODE function */
*(void **)(&fptr) = dlsym(x->backend_sohandle, fn_name);
if (NULL == fptr)
return -EOPNOTSUPP;
*instance = x;
return 0;
}
/**
* Erasure encode a data buffer
*
@ -308,23 +337,30 @@ int liberasurecode_encode(int desc,
const char *orig_data, uint64_t orig_data_size,
char **encoded_data, char **encoded_parity)
{
int ret = 0;
int (*fptr)() = NULL;
const char *fn_name = NULL;
const char *stub = FN_NAME(ENCODE);
ec_backend_t instance = liberasurecode_backend_instance_get_by_desc(desc);
if (instance == NULL)
return -ENOENT;
fn_name = lookup_fn_name(instance->common.fnmap, stub);
int blocksize = 0;
/* find the address of the ENCODE function */
*(void **)(&fptr) = dlsym(instance->backend_sohandle, fn_name);
ec_backend_t instance = NULL;
ret = liberasurecode_backend_lookup_instance_and_method(
desc, &instance, stub, fptr);
if (ret < 0)
goto out_error;
/* FIXME preprocess orig_data, get blocksize */
/* call the backend encode function passing it fptr */
instance->common.ops->encode(instance->backend_desc, fptr,
data, parity, blocksize);
ret = instance->common.ops->encode(
instance->backend_desc, fptr, instance->args,
encoded_data, encoded_parity, blocksize);
return 0;
out_error:
return ret;
}
/**
@ -341,23 +377,33 @@ int liberasurecode_decode(int desc,
uint64_t fragment_size, char **available_fragments,
char *out_data)
{
int ret = 0;
int (*fptr)() = NULL;
const char *fn_name = NULL;
const char *stub = FN_NAME(DECODE);
ec_backend_t instance = liberasurecode_backend_instance_get_by_desc(desc);
if (instance == NULL)
return -ENOENT;
fn_name = lookup_fn_name(instance->common.fnmap, stub);
int blocksize = 0;
char **data = NULL;
char **parity = NULL;
int *missing_idxs;
/* find the address of the DECODE function */
*(void **)(&fptr) = dlsym(instance->backend_sohandle, fn_name);
ec_backend_t instance = NULL;
ret = liberasurecode_backend_lookup_instance_and_method(
desc, &instance, stub, fptr);
if (ret < 0)
goto out_error;
/* FIXME preprocess available_fragments, split into data and parity,
* determine missing_idxs and calculate blocksize */
/* call the backend encode function passing it fptr */
instance->common.ops->decode(instance->backend_desc, fptr,
data, parity, missing_idxs, blocksize);
ret = instance->common.ops->decode(
instance->backend_desc, fptr, instance->args,
data, parity, missing_idxs, blocksize);
return 0;
out_error:
return ret;
}
/**
@ -376,24 +422,33 @@ int liberasurecode_reconstruct_fragment(int desc,
char **available_fragments, char **encoded_parity,
int destination_idx, char* out_fragment)
{
int ret = 0;
int (*fptr)() = NULL;
const char *fn_name = NULL;
const char *stub = FN_NAME(RECONSTRUCT);
ec_backend_t instance = liberasurecode_backend_instance_get_by_desc(desc);
if (instance == NULL)
return -ENOENT;
fn_name = lookup_fn_name(instance->common.fnmap, stub);
int blocksize = 0;
char **data = NULL;
char **parity = NULL;
int *missing_idxs;
/* find the address of the RECONSTRUCT function */
*(void **)(&fptr) = dlsym(instance->backend_sohandle, fn_name);
ec_backend_t instance = NULL;
ret = liberasurecode_backend_lookup_instance_and_method(
desc, &instance, stub, fptr);
if (ret < 0)
goto out_error;
/* FIXME preprocess available_fragments, split into data and parity,
* determine missing_idxs and calculate blocksize */
/* call the backend encode function passing it fptr */
instance->common.ops->reconstruct(instance->backend_desc, fptr,
data, parity, missing_idxs,
destination_idx, blocksize);
ret = instance->common.ops->reconstruct(
instance->backend_desc, fptr, instance->args,
data, parity, missing_idxs, destination_idx, blocksize);
return 0;
out_error:
return ret;
}
/**
@ -404,29 +459,33 @@ int liberasurecode_reconstruct_fragment(int desc,
* liberasurecode_instance_create)
* @missing_idx_list: list of indexes of missing elements
*
* @return a list of lists of indexes to rebuild data from
* (in 'fragments_needed')
* @return a list of lists (bitmaps) of indexes to rebuild data
* from (in 'fragments_needed')
*/
int liberasurecode_fragments_needed(int desc, int *missing_idxs,
int **fragments_needed)
int *fragments_needed)
{
int ret = 0;
int (*fptr)() = NULL;
const char *fn_name = NULL;
const char *stub = FN_NAME(FRAGSNEEDED);
ec_backend_t instance = liberasurecode_backend_instance_get_by_desc(desc);
if (instance == NULL)
return -ENOENT;
fn_name = lookup_fn_name(instance->common.fnmap, stub);
ec_backend_t instance = NULL;
/* find the address of the FRAGSNEEDED function */
*(void **)(&fptr) = dlsym(instance->backend_sohandle, fn_name);
ret = liberasurecode_backend_lookup_instance_and_method(
desc, &instance, stub, fptr);
if (ret < 0)
goto out_error;
/* FIXME preprocessing */
/* call the backend encode function passing it fptr */
instance->common.ops->fragments_needed(instance->backend_desc, fptr,
missing_idxs, fragments_needed);
ret = instance->common.ops->fragments_needed(
instance->backend_desc, fptr, instance->args,
missing_idxs, fragments_needed);
return 0;
out_error:
return ret;
}
/* ==~=*=~==~=*=~==~=*=~==~=*=~==~=* misc *=~==~=*=~==~=*=~==~=*=~==~=*=~== */