X-Git-Url: http://git.efficios.com/?p=babeltrace.git;a=blobdiff_plain;f=formats%2Fctf%2Ftypes%2Ffloat.c;h=2e0bd5ce57ea78b42994e13b4ddf05e19bc79ae5;hp=b2433bd8cb719c384e104e0f23d2e08d60bc355d;hb=0d69b916c5ba44b63a26aa038d416d6ee286306b;hpb=9b0422a038d313a812e1c862122ec1f2b70add9a diff --git a/formats/ctf/types/float.c b/formats/ctf/types/float.c index b2433bd8..2e0bd5ce 100644 --- a/formats/ctf/types/float.c +++ b/formats/ctf/types/float.c @@ -17,6 +17,14 @@ * The above copyright notice and this permission notice shall be included in * all copies or substantial portions of the Software. * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + * * Reference: ISO C99 standard 5.2.4 */ @@ -25,6 +33,7 @@ #include /* C99 floating point definitions */ #include /* C99 limits */ #include +#include /* * This library is limited to binary representation of floating point values. @@ -58,16 +67,38 @@ union doubleIEEE754 { #endif }; +/* + * This mutex protects the static temporary float and double + * declarations (static_float_declaration and static_double_declaration). + */ +static pthread_mutex_t float_mutex = PTHREAD_MUTEX_INITIALIZER; + static struct declaration_float *static_float_declaration, *static_double_declaration; struct pos_len { - size_t sign_start, exp_start, mantissa_start, len; + size_t len; }; -int _ctf_float_copy(struct stream_pos *destp, +static void float_lock(void) +{ + int ret; + + ret = pthread_mutex_lock(&float_mutex); + assert(!ret); +} + +static void float_unlock(void) +{ + int ret; + + ret = pthread_mutex_unlock(&float_mutex); + assert(!ret); +} + +static int _ctf_float_copy(struct bt_stream_pos *destp, struct definition_float *dest_definition, - struct stream_pos *srcp, + struct bt_stream_pos *srcp, const struct definition_float *src_definition) { int ret; @@ -134,7 +165,7 @@ int _ctf_float_copy(struct stream_pos *destp, return 0; } -int ctf_float_read(struct stream_pos *ppos, struct definition *definition) +int ctf_float_read(struct bt_stream_pos *ppos, struct bt_definition *definition) { struct definition_float *float_definition = container_of(definition, struct definition_float, p); @@ -142,11 +173,13 @@ int ctf_float_read(struct stream_pos *ppos, struct definition *definition) float_definition->declaration; struct ctf_stream_pos *pos = ctf_pos(ppos); union doubleIEEE754 u; - struct definition *tmpdef; + struct bt_definition *tmpdef; struct definition_float *tmpfloat; struct ctf_stream_pos destp; + struct mmap_align mma; int ret; + float_lock(); switch (float_declaration->mantissa->len + 1) { case FLT_MANT_DIG: tmpdef = static_float_declaration->p.definition_new( @@ -159,11 +192,14 @@ int ctf_float_read(struct stream_pos *ppos, struct definition *definition) NULL, 0, 0, "__tmpfloat"); break; default: - return -EINVAL; + ret = -EINVAL; + goto end; } tmpfloat = container_of(tmpdef, struct definition_float, p); + memset(&destp, 0, sizeof(destp)); ctf_init_pos(&destp, -1, O_RDWR); - destp.base = (char *) u.bits; + mmap_align_set_addr(&mma, (char *) u.bits); + destp.base_mma = &mma; destp.packet_size = sizeof(u) * CHAR_BIT; ctf_align_pos(pos, float_declaration->p.alignment); ret = _ctf_float_copy(&destp.parent, tmpfloat, ppos, float_definition); @@ -175,13 +211,18 @@ int ctf_float_read(struct stream_pos *ppos, struct definition *definition) float_definition->value = u.vd; break; default: - return -EINVAL; + ret = -EINVAL; + goto end_unref; } - definition_unref(tmpdef); + +end_unref: + bt_definition_unref(tmpdef); +end: + float_unlock(); return ret; } -int ctf_float_write(struct stream_pos *ppos, struct definition *definition) +int ctf_float_write(struct bt_stream_pos *ppos, struct bt_definition *definition) { struct definition_float *float_definition = container_of(definition, struct definition_float, p); @@ -189,11 +230,13 @@ int ctf_float_write(struct stream_pos *ppos, struct definition *definition) float_definition->declaration; struct ctf_stream_pos *pos = ctf_pos(ppos); union doubleIEEE754 u; - struct definition *tmpdef; + struct bt_definition *tmpdef; struct definition_float *tmpfloat; struct ctf_stream_pos srcp; + struct mmap_align mma; int ret; + float_lock(); switch (float_declaration->mantissa->len + 1) { case FLT_MANT_DIG: tmpdef = static_float_declaration->p.definition_new( @@ -206,11 +249,13 @@ int ctf_float_write(struct stream_pos *ppos, struct definition *definition) NULL, 0, 0, "__tmpfloat"); break; default: - return -EINVAL; + ret = -EINVAL; + goto end; } tmpfloat = container_of(tmpdef, struct definition_float, p); ctf_init_pos(&srcp, -1, O_RDONLY); - srcp.base = (char *) u.bits; + mmap_align_set_addr(&mma, (char *) u.bits); + srcp.base_mma = &mma; srcp.packet_size = sizeof(u) * CHAR_BIT; switch (float_declaration->mantissa->len + 1) { case FLT_MANT_DIG: @@ -220,30 +265,37 @@ int ctf_float_write(struct stream_pos *ppos, struct definition *definition) u.vd = float_definition->value; break; default: - return -EINVAL; + ret = -EINVAL; + goto end_unref; } ctf_align_pos(pos, float_declaration->p.alignment); ret = _ctf_float_copy(ppos, float_definition, &srcp.parent, tmpfloat); - definition_unref(tmpdef); + +end_unref: + bt_definition_unref(tmpdef); +end: + float_unlock(); return ret; } +static void __attribute__((constructor)) ctf_float_init(void) { static_float_declaration = - float_declaration_new(FLT_MANT_DIG, + bt_float_declaration_new(FLT_MANT_DIG, sizeof(float) * CHAR_BIT - FLT_MANT_DIG, BYTE_ORDER, __alignof__(float)); static_double_declaration = - float_declaration_new(DBL_MANT_DIG, + bt_float_declaration_new(DBL_MANT_DIG, sizeof(double) * CHAR_BIT - DBL_MANT_DIG, BYTE_ORDER, __alignof__(double)); } +static void __attribute__((destructor)) ctf_float_fini(void) { - declaration_unref(&static_float_declaration->p); - declaration_unref(&static_double_declaration->p); + bt_declaration_unref(&static_float_declaration->p); + bt_declaration_unref(&static_double_declaration->p); }