Tarantool development patches archive
 help / color / mirror / Atom feed
From: Vladislav Shpilevoy <v.shpilevoy@tarantool.org>
To: "n.pettik" <korablev@tarantool.org>, tarantool-patches@freelists.org
Subject: [tarantool-patches] Re: [PATCH 7/8] sql: clean-up affinity from SQL source code
Date: Wed, 30 Jan 2019 16:04:29 +0300	[thread overview]
Message-ID: <1487a209-af7b-5d1f-6fff-fc589782d571@tarantool.org> (raw)
In-Reply-To: <33150EBA-AB14-4089-8399-0FBD07C71BD8@tarantool.org>

Thanks for the fixes! See comments below.

>>> diff --git a/src/box/sql/vdbe.c b/src/box/sql/vdbe.c
>>> index 61d73b676..c3f596d4f 100644
>>> --- a/src/box/sql/vdbe.c
>>> +++ b/src/box/sql/vdbe.c
>>> @@ -2163,9 +2151,16 @@ case OP_Ge: {             /* same as TK_GE, jump, in1, in3 */
>>>                          break;
>>>                  }
>>>          } else {
>>> -               /* Neither operand is NULL.  Do a comparison. */
>>> -               affinity = pOp->p5 & AFFINITY_MASK;
>>> -               if (affinity>=AFFINITY_INTEGER) {
>>> +               /*
>>> +                * Neither operand is NULL. Do a comparison.
>>> +                * 15 is 1111 in a binary form.
>>> +                * Since all existing types can be fitted in 4 bits
>>> +                * (field_type_MAX == 10), it is enough to 'and'
>>> +                * p5 with this constant. Node that all other flags
>>> +                * that can be stored in p5 are >= 16.
>>> +                */
>>> +               affinity = pOp->p5 & 15;
>>
>> 4. Honestly, I did not expect it from you. Please, never use such
>> constants and assumptions about them in code. field_type_MAX = 10 can
>> be changed any day (for example, when we introduce decimal as a native
>> Tarantool data type, or decide to add datetime). In fact, it is already
>> not 10 - it is 9.
> 
> Oh, cmon. This place will explode only if number of types exceed 15.
> Not so soon, I guess (when was the last time we introduced new type?).
> So it won’t be my problem by the time it occurs.
> 
>> I propose you to either come up with a better solution or to use one of
>> my solutions:
>>
>> * return AFFINITY_MASK as P5_FIELD_TYPE_MASK, and add a static assertion
>>   that P5_FIELD_TYPE_MASK < (1 << bit_count(field_type)).
>>
>>   Or write in field_def.h something like this:
>>
>>       static_assert(bit_count(field_type) <= 4,
>>                     "size of enum field_type is used in "\
>>                     "VdbeOp.p5 to fit it into 4 bits”);
> 
> To be honest I don’t understand these bit assertions.
> Why can’t we simply check that field_type_MAX <= 15?
> 
> diff --git a/src/box/field_def.c b/src/box/field_def.c
> index b34d2ccd9..1a8074650 100644
> --- a/src/box/field_def.c
> +++ b/src/box/field_def.c
> @@ -33,6 +33,13 @@
>   #include "trivia/util.h"
>   #include "key_def.h"
>   
> +/**
> + * For detailed explanation see context of OP_Eq, OP_Lt etc
> + * opcodes in vdbe.c.
> + */
> +static_assert(field_type_MAX <= 15, "values of enum field_type "\
> +             "should fit into 4 bits of VdbeOp.p5");
> +
> 
> Also, as you may notice, I placed it to field_def.c
> Seems that field_def.h is used to generate module.h,
> which in turn doesn’t tolerate this kind of assert.

field_def.h is not copied to module.h entirely. Only
the code between /** \cond public */ and /** \endcond public */.
Please, put this assertion below /** \endcond public */.

> 
>>   To get bit_count during compilation you can specify it explicitly right
>>   after field_type_MAX in enum field_type so as to change it always
>>   together with field_type_MAX.
>>
> diff --git a/src/box/sql/wherecode.c b/src/box/sql/wherecode.c
> index 53445faf5..1f28893f6 100644
> --- a/src/box/sql/wherecode.c
> +++ b/src/box/sql/wherecode.c
>>> @@ -419,16 +419,15 @@ codeApplyAffinity(Parse * pParse, int base, int n, char *zAff)
>>>   static void
>>>   updateRangeAffinityStr(Expr * pRight,  /* RHS of comparison */
>>>                         int n,           /* Number of vector elements in comparison */
>>> -                      char *zAff)      /* Affinity string to modify */
>>> +                      enum field_type *zAff)   /* Affinity string to modify */
>>
>> 6. The same. In many other places too. Where you changed type and
>> usages of a variable, but kept its name.
> 
> I did it on purpose - to reduce diff, so that separate functional
> changes and non-functional such as renaming. Now fixed.

Small diff is good, but lets do not overemphasize. This patch states
that affinity is removed, and not only as a functionality, but from
the source code, but before your fixes it actually was not. It
complicated reading and understanding of the code.

> diff --git a/src/box/sql/vdbe.c b/src/box/sql/vdbe.c
> index 80d2fd0aa..358b69754 100644
> --- a/src/box/sql/vdbe.c
> +++ b/src/box/sql/vdbe.c
> @@ -2164,17 +2151,24 @@ case OP_Ge: {             /* same as TK_GE, jump, in1, in3 */
>  			break;
>  		}
>  	} else {
> -		/* Neither operand is NULL.  Do a comparison. */
> -		affinity = pOp->p5 & AFFINITY_MASK;
> -		if (affinity>=AFFINITY_INTEGER) {
> +		/*
> +		 * Neither operand is NULL. Do a comparison.
> +		 * 15 is 1111 in a binary form.
> +		 * Since all existing types can be fitted in 4 bits
> +		 * (field_type_MAX == 10), it is enough to 'and'
> +		 * p5 with this constant. Node that all other flags
> +		 * that can be stored in p5 are >= 16.

Firstly, as I said in the previous review, field_type_MAX == 9.
Secondly, please, do not use a constant. All of them (15, 111, 10, 16).
Instead of this huge comment full of constants just create a enum
value with an appropriate name, like FIELD_TYPE_MASK = 15, it is
even ok to put this name into field_def.h. Thirdly, not all p5 flags
are >= 16. But for these concrete opcodes it is so, luckily. At
least we have OPFLAG_NCHANGE, OPFLAG_EPHEM, OPFLAG_SEEKEQ etc -
they all are <= 15.

> +		 */
> +		enum field_type type = pOp->p5 & 15;
> +		if (sql_type_is_numeric(type)) {
>  			if ((flags1 | flags3)&MEM_Str) {
>  				if ((flags1 & (MEM_Int|MEM_Real|MEM_Str))==MEM_Str) {
> -					applyNumericAffinity(pIn1,0);
> +					mem_apply_numeric_type(pIn1, 0);
>  					testcase( flags3!=pIn3->flags); /* Possible if pIn1==pIn3 */
>  					flags3 = pIn3->flags;
>  				}
>  				if ((flags3 & (MEM_Int|MEM_Real|MEM_Str))==MEM_Str) {
> -					if (applyNumericAffinity(pIn3,0) != 0) {
> +					if (mem_apply_numeric_type(pIn3, 0) != 0) {
>  						diag_set(ClientError,
>  							 ER_SQL_TYPE_MISMATCH,
>  							 sqlite3_value_text(pIn3),

  reply	other threads:[~2019-01-30 13:04 UTC|newest]

Thread overview: 48+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2018-12-28  9:34 [tarantool-patches] [PATCH 0/8] Eliminate affinity from " Nikita Pettik
2018-12-28  9:34 ` [tarantool-patches] [PATCH 1/8] sql: remove SQLITE_ENABLE_UPDATE_DELETE_LIMIT define Nikita Pettik
2018-12-29 17:42   ` [tarantool-patches] " Vladislav Shpilevoy
2019-01-16 14:25     ` n.pettik
2018-12-28  9:34 ` [tarantool-patches] [PATCH 2/8] sql: use field type instead of affinity for type_def Nikita Pettik
2018-12-29 17:42   ` [tarantool-patches] " Vladislav Shpilevoy
2019-01-16 14:26     ` n.pettik
2018-12-28  9:34 ` [tarantool-patches] [PATCH 3/8] sql: remove numeric affinity Nikita Pettik
2018-12-29  9:01   ` [tarantool-patches] " Konstantin Osipov
2018-12-29 17:42   ` Vladislav Shpilevoy
2019-01-09  8:26     ` Konstantin Osipov
2019-01-16 14:26     ` n.pettik
2019-01-22 15:41       ` Vladislav Shpilevoy
2019-01-28 16:39         ` n.pettik
2019-01-30 13:04           ` Vladislav Shpilevoy
2019-02-01 16:39             ` n.pettik
2019-01-09  8:20   ` Konstantin Osipov
2018-12-28  9:34 ` [tarantool-patches] [PATCH 4/8] sql: replace affinity with field type for func Nikita Pettik
2018-12-28  9:34 ` [tarantool-patches] [PATCH 5/8] sql: replace field type with affinity for VDBE runtime Nikita Pettik
2018-12-29 17:42   ` [tarantool-patches] " Vladislav Shpilevoy
2019-01-16 14:26     ` n.pettik
2019-01-22 15:41       ` Vladislav Shpilevoy
2019-01-28 16:39         ` n.pettik
2019-01-30 13:04           ` Vladislav Shpilevoy
2019-02-01 16:39             ` n.pettik
2019-02-05 15:08               ` Vladislav Shpilevoy
2019-02-05 17:46                 ` n.pettik
2018-12-28  9:34 ` [tarantool-patches] [PATCH 6/8] sql: replace affinity with field type in struct Expr Nikita Pettik
2018-12-29 17:42   ` [tarantool-patches] " Vladislav Shpilevoy
2019-01-16 14:26     ` n.pettik
2019-01-22 15:41       ` Vladislav Shpilevoy
2019-01-28 16:39         ` n.pettik
2019-01-30 13:04           ` Vladislav Shpilevoy
2019-02-01 16:39             ` n.pettik
2019-02-05 15:08               ` Vladislav Shpilevoy
2019-02-05 17:46                 ` n.pettik
2018-12-28  9:34 ` [tarantool-patches] [PATCH 7/8] sql: clean-up affinity from SQL source code Nikita Pettik
2018-12-29 17:42   ` [tarantool-patches] " Vladislav Shpilevoy
2019-01-16 14:26     ` n.pettik
2019-01-22 15:41       ` Vladislav Shpilevoy
2019-01-28 16:40         ` n.pettik
2019-01-30 13:04           ` Vladislav Shpilevoy [this message]
2019-02-01 16:39             ` n.pettik
2019-02-05 15:08               ` Vladislav Shpilevoy
2019-02-05 17:46                 ` n.pettik
2018-12-28  9:34 ` [tarantool-patches] [PATCH 8/8] Remove affinity from field definition Nikita Pettik
2019-02-05 19:41 ` [tarantool-patches] Re: [PATCH 0/8] Eliminate affinity from source code Vladislav Shpilevoy
2019-02-08 13:37 ` Kirill Yukhin

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=1487a209-af7b-5d1f-6fff-fc589782d571@tarantool.org \
    --to=v.shpilevoy@tarantool.org \
    --cc=korablev@tarantool.org \
    --cc=tarantool-patches@freelists.org \
    --subject='[tarantool-patches] Re: [PATCH 7/8] sql: clean-up affinity from SQL source code' \
    /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