Tarantool development patches archive
 help / color / mirror / Atom feed
From: Serge Petrenko <sergepetrenko@tarantool.org>
To: Cyrill Gorcunov <gorcunov@gmail.com>
Cc: v.shpilevoy@tarantool.org, tarantool-patches@dev.tarantool.org
Subject: Re: [Tarantool-patches] [PATCH 1/2] box: speed up tuple_field_map_create
Date: Mon, 16 Nov 2020 10:34:42 +0300	[thread overview]
Message-ID: <b89573da-f62f-ca3b-e350-6d53ba33b914@tarantool.org> (raw)
In-Reply-To: <20201114180034.GM2021@grain>


14.11.2020 21:00, Cyrill Gorcunov пишет:
> On Sat, Nov 14, 2020 at 08:28:22PM +0300, Serge Petrenko wrote:
> ...
>> +static int
>> +tuple_field_map_create_plain(struct tuple_format *format, const char *tuple,
>> +			     bool validate, struct field_map_builder *builder)
>> +{
>> +#define check_field_type(field, pos) {					       \
>> +	if (validate &&							       \
>> +	    !field_mp_type_is_compatible(field->type, pos,		       \
>> +					 tuple_field_is_nullable(field))) {    \
>> +		diag_set(ClientError, ER_FIELD_TYPE, tuple_field_path(field),  \
>> +			 field_type_strs[field->type]);			       \
>> +		return -1;						       \
>> +	}								       \
>> +}

Hi! Thanks for the review!

> Serge, I'm completely not familiar with the code thus may be simply wrong but
> @check_field_type test for @validate first, right?
> ...
>> +
>> +	field = json_tree_lookup_entry(&format->fields, &format->fields.root,
>> +				       &token, struct tuple_field, token);
>> +	/* Check 1st field's type, but don't store offset to it. */
>> +	check_field_type(field, pos);
> 	check_field_type -> if (validate ...)
>
>> +	if (validate)
>> +		bit_clear(required_fields, field->id);
> and here we test for if (validate) again. Should not we simply
> drop if (validate) from check_field_type and call this macro under
> the caller's if? IOW
>
> 	if (validate) {
> 		check_field_type();
> 		bit_clear();
> 	}
>
> While check_field_type will be something like
>
> #define check_field_type(field, pos)					\
> ({									\
> 	bool nullable = tuple_field_is_nullable(field);			\
> 	if (!field_mp_type_is_compatible(field->type, pos, nullable)) {	\
> 		diag_set(ClientError, ER_FIELD_TYPE,			\
> 			tuple_field_path(field),			\
> 			field_type_strs[field->type]);			\
> 		return -1;						\
> 	}								\
> })


Yes, you're correct. Thanks for pointing this out!

I've amended the patch. Incremental diff is below.


>   - if I'm right we may fix it on top (actually since these two ifs are close
>     to each other they won't hurt hw branch predictor even in current form or
>     may be compiler merge these two basic blocks under one "if" flow)
>
>> +		check_field_type(field, pos);
>> +		if (validate)
>> +			bit_clear(required_fields, field->id);
> and here too.
>
>> +		if (field->offset_slot != TUPLE_OFFSET_SLOT_NIL &&
>> +		    field_map_builder_set_slot(builder, field->offset_slot,
>> +					       pos - tuple, MULTIKEY_NONE,
>> +					       0, NULL) != 0) {
>> +			return -1;
>> +		}
>> +	}


diff --git a/src/box/tuple_format.c b/src/box/tuple_format.c
index f2db521ea..ad2f251b4 100644
--- a/src/box/tuple_format.c
+++ b/src/box/tuple_format.c
@@ -861,15 +861,14 @@ static int
  tuple_field_map_create_plain(struct tuple_format *format, const char 
*tuple,
                              bool validate, struct field_map_builder 
*builder)
  {
-#define check_field_type(field, pos) 
{                                        \
-       if (validate && \
-           !field_mp_type_is_compatible(field->type, 
pos,                     \
- tuple_field_is_nullable(field))) {    \
+#define check_field_type(field, pos) 
({                                               \
+       bool nullable = 
tuple_field_is_nullable(field);                        \
+       if(!field_mp_type_is_compatible(field->type, pos, nullable)) 
{         \
                 diag_set(ClientError, ER_FIELD_TYPE, 
tuple_field_path(field),  \
field_type_strs[field->type]);                        \
                 return 
-1;                                                     \
} \
-}
+})

         struct region *region = &fiber()->gc;
         const char *pos = tuple;
@@ -904,9 +903,10 @@ tuple_field_map_create_plain(struct tuple_format 
*format, const char *tuple,
         field = json_tree_lookup_entry(&format->fields, 
&format->fields.root,
                                        &token, struct tuple_field, token);
         /* Check 1st field's type, but don't store offset to it. */
-       check_field_type(field, pos);
-       if (validate)
+       if (validate) {
+               check_field_type(field, pos);
                 bit_clear(required_fields, field->id);
+       }
         mp_next(&pos);

         for (uint32_t i = 1; i < defined_field_count; i++, mp_next(&pos)) {
@@ -914,9 +914,10 @@ tuple_field_map_create_plain(struct tuple_format 
*format, const char *tuple,
                 field = json_tree_lookup_entry(&format->fields,
&format->fields.root, &token,
                                                struct tuple_field, token);
-               check_field_type(field, pos);
-               if (validate)
+               if (validate) {
+                       check_field_type(field, pos);
                         bit_clear(required_fields, field->id);
+               }
                 if (field->offset_slot != TUPLE_OFFSET_SLOT_NIL &&
                     field_map_builder_set_slot(builder, field->offset_slot,
                                                pos - tuple, MULTIKEY_NONE,

-- 
Serge Petrenko

  reply	other threads:[~2020-11-16  7:34 UTC|newest]

Thread overview: 17+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-11-14 17:28 [Tarantool-patches] [PATCH 0/2] reduce performance degradation introduced by JSON path indices Serge Petrenko
2020-11-14 17:28 ` [Tarantool-patches] [PATCH 1/2] box: speed up tuple_field_map_create Serge Petrenko
2020-11-14 18:00   ` Cyrill Gorcunov
2020-11-16  7:34     ` Serge Petrenko [this message]
2020-11-20 23:26   ` Vladislav Shpilevoy
2020-11-23 13:50     ` Serge Petrenko
2020-11-24 22:33       ` Vladislav Shpilevoy
2020-12-01  8:48         ` Serge Petrenko
2020-12-01 22:04           ` Vladislav Shpilevoy
2020-12-02  9:53             ` Serge Petrenko
2020-11-14 17:28 ` [Tarantool-patches] [PATCH 2/2] box: use tuple_field_raw_by_part where possible Serge Petrenko
2020-11-20 23:26   ` Vladislav Shpilevoy
2020-11-23 13:51     ` Serge Petrenko
2020-11-24 22:33       ` Vladislav Shpilevoy
2020-12-01  8:48         ` Serge Petrenko
2020-12-01 22:04           ` Vladislav Shpilevoy
2020-11-16  7:50 ` [Tarantool-patches] [PATCH 0/2] reduce performance degradation introduced by JSON path indices Serge Petrenko

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=b89573da-f62f-ca3b-e350-6d53ba33b914@tarantool.org \
    --to=sergepetrenko@tarantool.org \
    --cc=gorcunov@gmail.com \
    --cc=tarantool-patches@dev.tarantool.org \
    --cc=v.shpilevoy@tarantool.org \
    --subject='Re: [Tarantool-patches] [PATCH 1/2] box: speed up tuple_field_map_create' \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox