← Back to team overview

kicad-developers team mailing list archive

Re: Concerns about clearing disagreements before committing.


Le 20/11/2011 00:10, Vladimir Uryvaev a écrit :
В сообщении от Суббота 19 ноября 2011 23:43:46 автор Dick Hollenbeck написал:

The key postings which illustrate my point and my understanding that there
was no concensus reached were these:

The first one carries the most weight, because it is from Jean-Pierre:


And my objections:

html 3)

"...I do not see the advantage..."
"I don't see it..."
"Its not clear to me..."
"Java explicitly avoided typedefs..."
"I hated virtually everything Microsoft introduced..."

Above are not look like an argument but like an personal opinion and/or
attitude. It is not an object for a discussion.

You do not see an advantage, but I see. I need for me to track anything
related lengths (with the help of a compiler).

Typedef, as any other tool, may help and may hurt. This depends on how you're
using it. DWORD and other typedef stuff was developed long before the Windows
has come. Mostly they're used where portability is an issue, because 'int' is
not so portable thing: name 'int' says only that it is an integer number of
range not less than -65535...+65535. But for portability in most cases much
more information needed, that's why in C99 (not C++) '[u]int*_t' was appeared
(see, they're just a typedefs). It is not the case in ADA where integer limits
are set explicitly, but it also have typedef-like syntax, just to define limits
only once. In Java AFAIR, typedef is superseeded by inheritance (in c++, int
cannot be inherited, only typedef'd).

OTOH if one specific technique made a rule it starts to hurt much, as happened
with Microsoft and their typedefs and hungarian notation (it is also not bad
then used wisely). Intention of MS's typedefs was to keep system call
parameters same machine type while in transition from 16 bit to 32 bit (int
and pointer are different when compiled in 16 bit and 32 bit modes!). Long time
only 32 bit machines rule the world and many programmers did not imagine that
int and long can have other width than 32 bit. But it can and it causes
portability issues.

My case is another. The value which LENGTH type carry is not an integer. It is
a physical length and it behave like a length, not like an integer. You do NOT
need keep in mind that machine stuff stands beyond its name. It is convenient
for me as a developer and switch its type just editing single line and see,
what's happen. If I suspect there are overflows somewhere, I may switch to
int64 or LIMITED_INT (which I introduce) and quickly catch them. If I suspect
roundind errors I may switch to long double (or even reload basic operations
to track all roundings in log!). When my work is finished I just switch back to
simplest and fastest type.

That's why I'm friend with typedefs.

In many cases all this stuff looks like:

     #ifdef NDEBUG // release
     typedef int X
     class X ..... (all that debug stuff)

Am I so clear now in that I do?

First, Thank you for your work, and the answers to our questions.

My main concern is about the complexity of the new code.

I explain:
If I read
    VECTOR_PCB m_Pos;      // pad Position on board
instead of
    wxPoint m_Pos;         // pad Position on board

I do not think this is a complex code.

But when I read:

// Returns the position of the pad.
const wxPoint D_PAD::ReturnShapePos()
    if( m_Offset[0] == ZERO_LENGTH && m_Offset[1] == ZERO_LENGTH )
        return TO_LEGACY_LU_WXP( m_Pos );

    wxPoint shape_pos;
    int     dX, dY;

    dX = TO_LEGACY_LU( m_Offset[0] );
    dY = TO_LEGACY_LU( m_Offset[1] );

    RotatePoint( &dX, &dY, m_Orient );

    shape_pos.x = TO_LEGACY_LU( m_Pos.x() ) + dX;
    shape_pos.y = TO_LEGACY_LU( m_Pos.y() ) + dY;

    return shape_pos;
I think this is a complex code.

The main reason is (in this case, but there are a lot of similar cases)
the pad position is in new units but its shape position is in old units, and there is no reason to do that.
(this shape pos is used in DRC and zone filling calculations and should be in internal units)

As a consequence, some parameters that have the same meaning are in new units and other are in old units.
And remember when I must use m_Pos.x and when I must use TO_LEGACY_LU( m_Pos.x() ) is not an easy task.

A side effect of these changes is the number of changes needed.
Obviously this will create bugs
Example: the line if( m_Offset[0] == ZERO_LENGTH && m_Offset[1] == ZERO_LENGTH ) fixes a bug
due to a copy/paste command: the actual string is currently:
if( m_Offset[0] == ZERO_LENGTH && m_Offset[0] == ZERO_LENGTH ).

Can you tell me if this complexity is just due to the fact your work is a work in progress
I mean, when all changes will be done, if lines like:
    shape_pos.x = TO_LEGACY_LU( m_Pos.x() ) + dX;
    shape_pos.y = TO_LEGACY_LU( m_Pos.y() ) + dY;
will be changed to
    shape_pos.x = m_Pos.x() + dX;
    shape_pos.y = m_Pos.y() + dY;
that is a "reasonable" code.

If fact, from my point of view (I may be wrong) change from old to new internal units is mainly located
in Save/Read functions (that should handle a scaling factor),
and should not involve many changes outside these functions.

Other changes (but this is also the case in this new code) are related to some constants in constructors and some dialogs.

Note in dialogs, values are always converted to string using a scale factor depending on the internal units
see PutValueInLocalUnits , ReturnValueFromString functions and m_InternalUnits member of EDA_DRAW_FRAME).

Draw functions (due to very different values of draw scale factors) could have some issues, that can be fixed by a prescaling factor (in new code, this is already done).

I understand your code is mainly to trap bugs relative to the new internal values throughout the Kicad code.
But are you sure this changes (new internal unit value) can create bugs everywhere.
(changes everywhere can create bugs everywhere)

outside Read/Write and constructors functions (very few files) the main hazard is related to arithmetic overflow
Note this can happen only with 32 bits machines.

I am thinking there are only few functions that can create this problem:
mainly some (duplicated code) that calculate if 2 segments are collinear or use the slope of a segment in intermediate calculations.
This is easy to fix, just find them ... and note they are currently already broken.
An other overflow possibility is inside BOOST::polygon classes, but the current new code cannot fix that.

Again, Thanks.

However I agree with you that we all could have been clearer.

In my mind, when Jean-Pierre objects to something, I tend to take that with
a fairly heavily weighted factor, so my lasting perception of the
conversation was obviously different than yours.

When in discussion, personality should not be weighting factor, only the sense
of arguments. After the discussion authorized person makes the decision.
If you decide, that I should not do what I do in kicad, i will not do it there
(i'll do it somewhere else). If you decide that it is not needed in KiCad or
have to be done in another way, i understand.

I do not know your level of knowledge and expirience and you all do not know
my, so we all can not decide how strong our arguments should be.

Putting that behind us now, are you willing to reopen the discussion and
answer some questions by others and myself?

It seems I understood
incorrectly what should I do, and what shouldn't.

В сообщении от Пятница 18 ноября 2011 21:23:21 вы написали:
1) Regarding the use of "class wrappers for integers", you never
completed the argument to a point of having built a consensus.  Both
Jean-Pierre, Lorenzo, and myself expressed disagreement towards this
plan in the

following thread:
I do not realize what sort of argument you're want from me. Is it known
method for you to encourage the compiler to catch possible bugs?

9. html

Independent of how good or bad the idea is or was, we now have a
political problem, and that is that we currently think you have some
"team player" issues to improve on.  Perhaps an apology and a
continuation of the original conversation is needed.

Seemingly I'm bad 'team player'. I apologize.

Thanks for making this effort.  We are in fact a team, and what we need are
team players, especially in those positions which have commit rights to
the testing-branch.

a) Star * to be after LENGTH_UNIT_DESC not before UnitDescription()
b) { bracket to be on its own line after first line of function.
c) switch() needs whitespace around the aUnit on both ends.
d) { brack to be on its own line in switch.
e) switch indenting of cases is wrong, cases to be at same level as
switch() f) single line comments are to be C++ not C style..

bcde) was my fault, I still did not spent 15 s to reformat 5 lines of
code, but... It seems my eyes cheat me, but I still do not see the
*rules* for a) and f).

a)&  f) are in the coding standards document, but there is also the tens of
thousands of lines of code in the project which already act as examples.

Can you cite the *rule*, please? Examples are not rules, though.

My 'native' style too different from what KiCAD use but I believe we all should
be tolerant to others. I cannot take as an argument that 'makes it difficult to
see' (Wayne wrote), because many people (outside KiCAD project) write like me
and read such code and have no difficulties.

However I do not intend to break or change the rules.

I saw this bug in a recent revision pertaining to

Clearance 40.000000
TrackWidth 40.000000
ViaDia 180.000000
ViaDrill 100.000000
uViaDia 200.000000
uViaDrill 50.000000

This raised an alarm with me.  I don't like unnecessary trailing zeros, in
any case.

I cannot reproduce it. If it is still not work as expected, I apologize.

p. s.
Do you want to know my (and russian KiCAD developers I met today) point
of view on KiCad sources? Do you find easy to read well formatted
spaghetti like code?..

Yes to the above, but only if you think this would be helpful to the
project, or to our perception of you.

I do not intend to offend any of developers, but all sad below is what we
agree in.

Altough too much effort in whitespaces, linefeeds and letter case, in general
kicad source is bad designed, overcomplicated, ineffective, and thus need much
rewrite and refactoring.

For example, that's I've found.

* Several definitions of macros abs, max, MAX, min, MIN and similar in different
headers, and sometimes sources (already fixed in my last commit), it seems they
are not alone.

* Much stuff related to class internals spreaded all around sources, like this
one dealing with TEXTE internals found in MODULE method:
             pt_texte = (TEXTE_MODULE*) PtStruct;
             pt_texte->m_Pos.y -= m_Pos.y;
             pt_texte->m_Pos.y  = -pt_texte->m_Pos.y;
             pt_texte->m_Pos.y += m_Pos.y;
             NEGATE( pt_texte->m_Pos0.y );
             pt_texte->m_Mirror = false;
             NEGATE_AND_NORMALIZE_ANGLE_POS( pt_texte->m_Orient );

* switch() where polymorphism fit much better (similar to above).

* Lots of hardcoded constants throughout the code.

I understand that much of it is not a result of someone's incompetence and a
result of long-long 'evolution', but in my opinion it retards KiCAD
development too much.

I think it would be best if lead developers take all in their
plans, e. g. by creating nice blueprints which we all will take cue from.

Jean-Pierre CHARRAS

Follow ups