-
Notifications
You must be signed in to change notification settings - Fork 97
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
p9_dd_container: simple generic standalone DD level container
Change-Id: I4c9d8cb28d4ae6a8b21c87ebaad07c1fd7163b85 Reviewed-on: http://ralgit01.raleigh.ibm.com/gerrit1/39588 Tested-by: Jenkins Server <pfd-jenkins+hostboot@us.ibm.com> Reviewed-by: Claus M. Olsen <cmolsen@us.ibm.com> Reviewed-by: Sumit Kumar <sumit_kumar@in.ibm.com> Reviewed-by: Martin Peschke <mpeschke@de.ibm.com> Reviewed-on: http://ralgit01.raleigh.ibm.com/gerrit1/40758 Tested-by: Jenkins OP Build CI <op-jenkins+hostboot@us.ibm.com> Tested-by: FSP CI Jenkins <fsp-CI-jenkins+hostboot@us.ibm.com> Reviewed-by: Daniel M. Crowell <dcrowell@us.ibm.com>
- Loading branch information
1 parent
c3ea903
commit 3736d09
Showing
5 changed files
with
385 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,262 @@ | ||
/* IBM_PROLOG_BEGIN_TAG */ | ||
/* This is an automatically generated prolog. */ | ||
/* */ | ||
/* $Source: src/import/chips/p9/utils/imageProcs/p9_dd_container.c $ */ | ||
/* */ | ||
/* OpenPOWER HostBoot Project */ | ||
/* */ | ||
/* Contributors Listed Below - COPYRIGHT 2017 */ | ||
/* [+] International Business Machines Corp. */ | ||
/* */ | ||
/* */ | ||
/* Licensed under the Apache License, Version 2.0 (the "License"); */ | ||
/* you may not use this file except in compliance with the License. */ | ||
/* You may obtain a copy of the License at */ | ||
/* */ | ||
/* http://www.apache.org/licenses/LICENSE-2.0 */ | ||
/* */ | ||
/* Unless required by applicable law or agreed to in writing, software */ | ||
/* distributed under the License is distributed on an "AS IS" BASIS, */ | ||
/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or */ | ||
/* implied. See the License for the specific language governing */ | ||
/* permissions and limitations under the License. */ | ||
/* */ | ||
/* IBM_PROLOG_END_TAG */ | ||
|
||
#include <stdint.h> | ||
#include <stddef.h> | ||
#include <stdlib.h> | ||
#include <endian.h> | ||
#include <string.h> | ||
#include <stdio.h> | ||
|
||
#include "p9_dd_container.h" | ||
|
||
int p9_dd_validate(struct p9_dd_cont* i_cont) | ||
{ | ||
if (!i_cont) | ||
{ | ||
return P9_DD_FAILURE_DOES_NOT_EXIST; | ||
} | ||
|
||
if (be32toh(i_cont->iv_magic) != P9_DD_CONTAINER_MAGIC) | ||
{ | ||
return P9_DD_FAILURE_BROKEN; | ||
} | ||
|
||
// may want to check here for holes or overlap as to stored blocks | ||
|
||
return P9_DD_SUCCESS; | ||
} | ||
|
||
// iterates through all dd level blocks | ||
struct p9_dd_block* p9_dd_next(struct p9_dd_iter* io_iter) | ||
{ | ||
struct p9_dd_block* block; | ||
|
||
if (!io_iter || | ||
!io_iter->iv_cont || | ||
io_iter->iv_idx >= io_iter->iv_cont->iv_num) | ||
{ | ||
return NULL; | ||
} | ||
|
||
block = &(io_iter->iv_cont->iv_blocks)[io_iter->iv_idx]; | ||
io_iter->iv_idx++; | ||
|
||
return block; | ||
} | ||
|
||
uint8_t* p9_dd_addr(struct p9_dd_cont* i_cont, uint32_t i_offset) | ||
{ | ||
return (uint8_t*)i_cont + i_offset; | ||
} | ||
|
||
void p9_dd_betoh(struct p9_dd_block* i_block_be, | ||
struct p9_dd_block* io_block_he) | ||
{ | ||
io_block_he->iv_offset = be32toh(i_block_be->iv_offset); | ||
io_block_he->iv_size = be32toh(i_block_be->iv_size); | ||
io_block_he->iv_dd = i_block_be->iv_dd; | ||
} | ||
|
||
// returns address of dd level content (without meta data) | ||
int p9_dd_get(uint8_t* i_cont, uint8_t i_dd, uint8_t** o_buf, uint32_t* o_size) | ||
{ | ||
struct p9_dd_cont* cont = (struct p9_dd_cont*)i_cont; | ||
struct p9_dd_iter iter = P9_DD_ITER_INIT(cont); | ||
struct p9_dd_block* block; | ||
struct p9_dd_block block_he; | ||
int rc; | ||
|
||
rc = p9_dd_validate(cont); | ||
|
||
if (rc != P9_DD_SUCCESS) | ||
{ | ||
return rc; | ||
} | ||
|
||
while ((block = p9_dd_next(&iter))) | ||
{ | ||
if (block->iv_dd == i_dd) | ||
{ | ||
p9_dd_betoh(block, &block_he); | ||
*o_buf = p9_dd_addr(cont, block_he.iv_offset); | ||
*o_size = block_he.iv_size; | ||
return P9_DD_SUCCESS; | ||
} | ||
} | ||
|
||
return P9_DD_FAILURE_NOT_FOUND; | ||
} | ||
|
||
uint32_t p9_dd_size_meta(struct p9_dd_cont* i_cont) | ||
{ | ||
return (i_cont ? | ||
(sizeof(struct p9_dd_cont) + | ||
sizeof(struct p9_dd_block) * i_cont->iv_num) : | ||
0); | ||
} | ||
|
||
// assumes only API (p9_dd_add()) used to create container, | ||
// that is, last block header points to block with biggest offset | ||
uint32_t p9_dd_size(struct p9_dd_cont* i_cont) | ||
{ | ||
struct p9_dd_block* last; | ||
|
||
if (!i_cont) | ||
{ | ||
return 0; | ||
} | ||
|
||
if (!i_cont->iv_num) | ||
{ | ||
return p9_dd_size_meta(i_cont); | ||
} | ||
|
||
last = &(i_cont->iv_blocks)[i_cont->iv_num - 1]; | ||
|
||
return be32toh(last->iv_offset) + be32toh(last->iv_size); | ||
} | ||
|
||
struct p9_dd_cont* p9_dd_create(void) | ||
{ | ||
struct p9_dd_cont* cont; | ||
|
||
cont = malloc(sizeof(struct p9_dd_cont)); | ||
|
||
if (!cont) | ||
{ | ||
return cont; | ||
} | ||
|
||
cont->iv_magic = htobe32(P9_DD_CONTAINER_MAGIC); | ||
cont->iv_num = 0; | ||
|
||
return cont; | ||
} | ||
|
||
// enlarges (reallocates) container and copies dd level block into container | ||
int p9_dd_add( | ||
uint8_t** io_cont, uint32_t* o_cont_size, uint8_t i_dd, | ||
uint8_t* i_buf, uint32_t i_buf_size) | ||
{ | ||
struct p9_dd_cont* cont = (struct p9_dd_cont*)*io_cont; | ||
|
||
uint8_t* dupl_buf; | ||
uint32_t dupl_size; | ||
|
||
uint32_t enlarged; | ||
|
||
int rc; | ||
|
||
uint8_t* others_addr_new; | ||
uint8_t* others_addr_old; | ||
uint32_t others_size; | ||
struct p9_dd_block* others_block; | ||
|
||
uint8_t* this_addr; | ||
uint32_t this_offs; | ||
struct p9_dd_block* this_block; | ||
|
||
struct p9_dd_iter iter = P9_DD_ITER_INIT(NULL); | ||
|
||
// handle duplicates and initial setup of empty container | ||
rc = p9_dd_get(*io_cont, i_dd, &dupl_buf, &dupl_size); | ||
|
||
switch (rc) | ||
{ | ||
case P9_DD_FAILURE_NOT_FOUND : | ||
break; | ||
|
||
case P9_DD_FAILURE_DOES_NOT_EXIST : | ||
cont = p9_dd_create(); | ||
|
||
if (!cont) | ||
{ | ||
return P9_DD_FAILURE_NOMEM; | ||
} | ||
|
||
break; | ||
|
||
case P9_DD_SUCCESS : | ||
return P9_DD_FAILURE_DUPLICATE; | ||
|
||
default : | ||
return rc; | ||
} | ||
|
||
// size of enlarged container | ||
enlarged = p9_dd_size(cont) + sizeof(struct p9_dd_block) + i_buf_size; | ||
|
||
// re-allocate to enlarge container (content is retained and consistent) | ||
cont = realloc(cont, enlarged); | ||
|
||
if (!cont) | ||
{ | ||
return P9_DD_FAILURE_NOMEM; | ||
} | ||
|
||
// offsets and size of existing bufs | ||
others_addr_old = p9_dd_addr(cont, p9_dd_size_meta(cont)); | ||
others_addr_new = others_addr_old + sizeof(struct p9_dd_block); | ||
others_size = p9_dd_size(cont) - p9_dd_size_meta(cont); | ||
|
||
// meta data, offset and address of new buf | ||
this_block = (struct p9_dd_block*)others_addr_old; | ||
this_offs = p9_dd_size(cont) + sizeof(struct p9_dd_block); | ||
this_addr = p9_dd_addr(cont, this_offs); | ||
|
||
// fix offsets of existing bufs | ||
iter.iv_cont = cont; | ||
|
||
while ((others_block = p9_dd_next(&iter))) | ||
{ | ||
others_block->iv_offset = | ||
htobe32(be32toh(others_block->iv_offset) + | ||
sizeof(struct p9_dd_block)); | ||
} | ||
|
||
// move existing bufs | ||
memmove(others_addr_new, others_addr_old, others_size); | ||
|
||
// copy new buf into container | ||
memcpy(this_addr, i_buf, i_buf_size); | ||
|
||
// fill in meta data for new buf | ||
memset(this_block, sizeof(struct p9_dd_block), 0); | ||
this_block->iv_offset = htobe32(this_offs); | ||
this_block->iv_size = htobe32(i_buf_size); | ||
this_block->iv_dd = i_dd; | ||
this_block->iv_reserved[0] = 0; | ||
this_block->iv_reserved[1] = 0; | ||
this_block->iv_reserved[2] = 0; | ||
|
||
// increase number off DD level blocks in container | ||
(cont)->iv_num++; | ||
|
||
*io_cont = (uint8_t*)cont; | ||
*o_cont_size = enlarged; | ||
|
||
return P9_DD_SUCCESS; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,94 @@ | ||
/* IBM_PROLOG_BEGIN_TAG */ | ||
/* This is an automatically generated prolog. */ | ||
/* */ | ||
/* $Source: src/import/chips/p9/utils/imageProcs/p9_dd_container.h $ */ | ||
/* */ | ||
/* OpenPOWER HostBoot Project */ | ||
/* */ | ||
/* Contributors Listed Below - COPYRIGHT 2017 */ | ||
/* [+] International Business Machines Corp. */ | ||
/* */ | ||
/* */ | ||
/* Licensed under the Apache License, Version 2.0 (the "License"); */ | ||
/* you may not use this file except in compliance with the License. */ | ||
/* You may obtain a copy of the License at */ | ||
/* */ | ||
/* http://www.apache.org/licenses/LICENSE-2.0 */ | ||
/* */ | ||
/* Unless required by applicable law or agreed to in writing, software */ | ||
/* distributed under the License is distributed on an "AS IS" BASIS, */ | ||
/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or */ | ||
/* implied. See the License for the specific language governing */ | ||
/* permissions and limitations under the License. */ | ||
/* */ | ||
/* IBM_PROLOG_END_TAG */ | ||
|
||
#ifndef _P9_DD_CONTAINER_H_ | ||
#define _P9_DD_CONTAINER_H_ | ||
|
||
#include <stdint.h> | ||
|
||
#define P9_DD_CONTAINER_MAGIC 0x4444434F // "DDCO" | ||
|
||
#define P9_DD_SUCCESS 0 | ||
#define P9_DD_FAILURE_BROKEN 1 | ||
#define P9_DD_FAILURE_NOMEM 2 | ||
#define P9_DD_FAILURE_NOT_FOUND 3 | ||
#define P9_DD_FAILURE_DOES_NOT_EXIST 4 | ||
#define P9_DD_FAILURE_DUPLICATE 5 | ||
|
||
// header for each dd level block inside container | ||
struct p9_dd_block | ||
{ | ||
uint32_t iv_offset; | ||
uint32_t iv_size; | ||
uint8_t iv_dd; | ||
uint8_t iv_reserved[3]; | ||
}; | ||
|
||
// container header | ||
struct p9_dd_cont | ||
{ | ||
uint32_t iv_magic; | ||
uint8_t iv_num; | ||
uint8_t iv_reserved[3]; | ||
struct p9_dd_block iv_blocks[0]; | ||
}; | ||
|
||
// iterator that can be used to iterate through all dd level blocks | ||
struct p9_dd_iter | ||
{ | ||
struct p9_dd_cont* iv_cont; | ||
uint8_t iv_idx; | ||
}; | ||
|
||
// initialisation of iterator | ||
#define P9_DD_ITER_INIT(dd_cont) { .iv_cont = (dd_cont), .iv_idx = 0 } | ||
|
||
#ifdef __cplusplus | ||
extern "C" { | ||
#endif | ||
|
||
// validates container | ||
int p9_dd_validate(struct p9_dd_cont* i_cont); | ||
|
||
void p9_dd_betoh(struct p9_dd_block* i_block_be, | ||
struct p9_dd_block* io_block_he); | ||
|
||
// iterates through all dd level blocks | ||
struct p9_dd_block* p9_dd_next(struct p9_dd_iter* io_iter); | ||
|
||
// returns address of dd level content (without meta data) | ||
int p9_dd_get( | ||
uint8_t* i_cont, uint8_t i_dd, uint8_t** o_buf, uint32_t* o_size); | ||
|
||
// enlarges (reallocates) container and copies dd level block into container | ||
int p9_dd_add( | ||
uint8_t** io_cont, uint32_t* o_cont_size, uint8_t i_dd, | ||
uint8_t* i_buf, uint32_t i_buf_size); | ||
|
||
#ifdef __cplusplus | ||
} | ||
#endif | ||
|
||
#endif |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,27 @@ | ||
# IBM_PROLOG_BEGIN_TAG | ||
# This is an automatically generated prolog. | ||
# | ||
# $Source: src/import/chips/p9/utils/imageProcs/p9_dd_container.mk $ | ||
# | ||
# OpenPOWER HostBoot Project | ||
# | ||
# Contributors Listed Below - COPYRIGHT 2016,2017 | ||
# [+] International Business Machines Corp. | ||
# | ||
# | ||
# Licensed under the Apache License, Version 2.0 (the "License"); | ||
# you may not use this file except in compliance with the License. | ||
# You may obtain a copy of the License at | ||
# | ||
# http://www.apache.org/licenses/LICENSE-2.0 | ||
# | ||
# Unless required by applicable law or agreed to in writing, software | ||
# distributed under the License is distributed on an "AS IS" BASIS, | ||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or | ||
# implied. See the License for the specific language governing | ||
# permissions and limitations under the License. | ||
# | ||
# IBM_PROLOG_END_TAG | ||
PROCEDURE=p9_dd_container | ||
$(call BUILD_PROCEDURE) | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.