May 19, 2013
On 05/19/2013 09:42 PM, Walter Bright wrote:
> On 5/19/2013 12:31 PM, Minas Mina wrote:
>> On Sunday, 19 May 2013 at 18:30:09 UTC, deadalnix wrote:
>>> void buzz(Foo f) {
>>>     f.foo(); // Rely in faith. It is invalid and way easier to write
>>> than the
>>> valid code, which is THE recipe for it to spread.
>>> }
>>
>> Shouldn't this throw a NullPointerSomething?
>
> It throws a seg fault at runtime. It *is* checked for by the hardware.

Yes, but this code looks like it calls method 'foo', which is probably its intention. Hence it is buggy.

D's current answer is the following:

void buzz(Foo f)in{assert(!!f);}body{
    f.foo();
}

May 19, 2013
On 5/19/2013 11:37 AM, deadalnix wrote:
> On Sunday, 19 May 2013 at 18:27:08 UTC, Walter Bright wrote:
>> oldVar isn't being default constructed in your example, nor can I see why
>> you'd need a default constructor in order to use RAII for save/restore.
>
> I need to save the value at construction and restore at destruction. I don't
> need any runtime parameter at construction.

The saved value is initialized with the value to be saved. This is not default construction.
May 19, 2013
On 05/19/2013 09:10 PM, Andrei Alexandrescu wrote:
>> I encourage you to look at this :
>> http://www.infoq.com/presentations/Null-References-The-Billion-Dollar-Mistake-Tony-Hoare
>>
>
> I read it. I don't buy it. Yeah, it's a point, but it's largely
> exaggerated for dramatic purposes.

(It is a talk.)
May 19, 2013
On Sunday, 19 May 2013 at 19:42:59 UTC, Walter Bright wrote:
> On 5/19/2013 12:31 PM, Minas Mina wrote:
>> On Sunday, 19 May 2013 at 18:30:09 UTC, deadalnix wrote:
>>> void buzz(Foo f) {
>>>    f.foo(); // Rely in faith. It is invalid and way easier to write than the
>>> valid code, which is THE recipe for it to spread.
>>> }
>>
>> Shouldn't this throw a NullPointerSomething?
>
> It throws a seg fault at runtime. It *is* checked for by the hardware.

I think there is difference between catching exception and saving
data which you have typed for some period and letting harware
"check" the exception for you meanwile loosing your work.
May 19, 2013
On 5/19/13 3:36 PM, deadalnix wrote:
> On Sunday, 19 May 2013 at 19:10:28 UTC, Andrei Alexandrescu wrote:
>> No, your argument is ridiculous. You make a yarn with precious little
>> detail that describes for everything everyone knows a textbook race
>> condition, essentially ask that you are taking by your word that
>> non-null would miraculously solve it, and, to add insult to injury,
>> and when we don't buy it, you put the burden of proof on us. This is
>> quite a trick, my hat is off to you.
>>
>
> I described a very usual null bug : something is set to null, then to a
> specific value. It is assumed not to be null. In a specific case it is
> null and everything explode.
>
> The concurrent context here made it especially hard to debug, but isn't
> the cause of the bug.
>
> Additionally, if you don't have enough information to understand what
> I'm saying, you are perfectly allowed to ask for additional details This
> isn't a shame.

Your argument has been destroyed so no need to ask details about it. Replace "null" with "invalid state" and it's the same race in any system. Let's move on.

>> What's the safety hole? Objects of large static size?
>>
>
> Limiting object size isn't going to cut it. Or must be super restrictive
> (the protection is 4kb on some systems).

Well you got to do what you got to do. Field accesses for objects larger than 4KB would have to be checked in @safe code.

>>> We
>>> can't even add check only on some edges cases as D also have values
>>> types. The only solution we are left with that is really safe is to null
>>> check every dereference or give up on @safe.
>>
>> How about using NonNull. We won't change the language at this point to
>> make non-nullable references by default. Even you acknowledged that
>> that's not practical. So now you contradict your own affirmation. What
>> exactly do you sustain, and what are you asking for?
>>
>
> 1/ NonNull do not work.

You made the argument that although it does work, people will not use it because it's not the default. That's not quite "does not work". This also ruins your point because if people don't find it worth writing NonNull!T instead of T, it means non-null doesn't buy them anything worthwhile.

> 2/ It isn't because it is too late to solve a problem that it magically
> isn't a problem anymore.

You are blowing it out of proportion. Null references are hardly even on the radar of the bug classes I'm encountering in the style of programming of the three groups I worked in at Facebook, and also my previous employers. People I meet at conferences and consulting gigs never mention null references as a real problem, although I very often ask about problems. I find it difficult to agree with you just to be nice.

>>> Most new languages removed nullable by default, or limited its uses
>>> (scala for instance, allow for null for limited scope).
>>
>> So what do you realistically think we should do, seeing that we're
>> aiming at stability?
>>
>
> Acknowledge it was a mistake and move on.

I'd give it more thought if we designed D from scratch. I think it's safe to move on. At any rate, I'd love if we got NonNull working nicely so we accumulate more experience with it.


Andrei
May 19, 2013
On 5/19/2013 12:10 PM, deadalnix wrote:
> On Sunday, 19 May 2013 at 18:46:31 UTC, Walter Bright wrote:
>>> You also never provided any convincing solution to the safety hole. We can't
>>> even add check only on some edges cases as D also have values types. The only
>>> solution we are left with that is really safe is to null check every dereference
>>> or give up on @safe.
>>
>> Please don't make us guess what exactly you mean by this.
>
> This isn't new and I discussed that again and again.
>
> When you dereference null, you hit the first plage, which is protected on most
> systems. But if you access an element with sufficient offset you bypass all
> protections provided by the type system and you are back in unsafe world.


And we've replied to this before. But when you say "give up on @safe", that implies a far more serious issue, so I want to make sure what you're talking about.

I agree that we need to deal with the issue. But on a practical note, if we solve 99% of the @safe issues, and fail at 1%, that doesn't mean there is no value to @safe and we should give up on it.

May 19, 2013
On 5/19/13 3:58 PM, Timon Gehr wrote:
> On 05/19/2013 09:10 PM, Andrei Alexandrescu wrote:
>>> I encourage you to look at this :
>>> http://www.infoq.com/presentations/Null-References-The-Billion-Dollar-Mistake-Tony-Hoare
>>>
>>>
>>
>> I read it. I don't buy it. Yeah, it's a point, but it's largely
>> exaggerated for dramatic purposes.
>
> (It is a talk.)

(I read a transcript.)

Andrei
May 19, 2013
On 5/19/13 4:05 PM, Walter Bright wrote:
> On 5/19/2013 12:10 PM, deadalnix wrote:
>> On Sunday, 19 May 2013 at 18:46:31 UTC, Walter Bright wrote:
>>>> You also never provided any convincing solution to the safety hole.
>>>> We can't
>>>> even add check only on some edges cases as D also have values types.
>>>> The only
>>>> solution we are left with that is really safe is to null check every
>>>> dereference
>>>> or give up on @safe.
>>>
>>> Please don't make us guess what exactly you mean by this.
>>
>> This isn't new and I discussed that again and again.
>>
>> When you dereference null, you hit the first plage, which is protected
>> on most
>> systems. But if you access an element with sufficient offset you
>> bypass all
>> protections provided by the type system and you are back in unsafe world.
>
>
> And we've replied to this before. But when you say "give up on @safe",
> that implies a far more serious issue, so I want to make sure what
> you're talking about.
>
> I agree that we need to deal with the issue. But on a practical note, if
> we solve 99% of the @safe issues, and fail at 1%, that doesn't mean
> there is no value to @safe and we should give up on it.

Almost safe == almost pregnant. @safe must be 100% safe.

Andrei


May 19, 2013
On Sunday, 19 May 2013 at 20:03:24 UTC, Andrei Alexandrescu wrote:
> Well you got to do what you got to do. Field accesses for objects larger than 4KB would have to be checked in @safe code.

Isn't the solution as easy as doing:
OR PTR:[address], 0
the same way it's done for the stack?

The offset it known at compile time in most cases, so the command would be required only if both:
* The object is larger than target OS' guard page size.
* The position is greater than target OS' guard page size, OR is unknown at compile time.
May 19, 2013
On 5/19/2013 12:36 PM, deadalnix wrote:
> I C or C++ you are doomed to manage reference as you need to for memory
> management purpose. In garbage collected languages, you ends up with way more
> unmanaged references, because the GC take care of them. Doing so you multiply
> the surface area where null bug can strike.

I still don't see the connection.

I've had many more null pointer bugs in non-gc code than in gc code, but I attribute that to my being a better programmer in gc code because I did that later and was more aware of issues.