Memory safe in D

Petar Petar
Wed Mar 13 16:06:14 UTC 2024


On Wednesday, 13 March 2024 at 06:05:35 UTC, Walter Bright wrote:
> [..]
>
> Consider the following:
> ```
> class A { void bar(); }
>
> void foo(int i) {
>     A a;
>     if (i) a = new A();
>     ...
>     if (i) a.bar();
> }
> ```
> What happens if we apply data flow analysis to determine the 
> state of `a` when it calls `bar()`? It will determine that `a` 
> has the possible values (`null`, new A()`). Hence, it will give 
> an error that `a` is possibly null at that point.
>
> Yet the code is correct, not buggy.
>
> Yes, the compiler could figure out that `i` is the same, but 
> the conditions can be more complex such that the compiler 
> cannot figure it out (the halting problem).
>
> So that doesn't work.
>
> We could lower `a.bar()` to `NullCheck(a).bar()` which throws 
> an exception if `a` is null. But what have we gained there? 
> Nothing. The program still aborts with an exception, just like 
> if the hardware checked. Except we've got this manual check 
> that costs extra code and CPU time.
>
> BTW, doing data flow analysis is very expensive in terms of 
> compiler run time. The optimizer does it, but running the 
> optimizer is optional for that reason.

Here's how TypeScript deals with this problem:

```ts
class A { bar() {} }

function foo(i: number) {
     let a: A;
     if (i) a = new A();

     if (i) a.bar(); // Error: Variable 'a' is used before being 
assigned.
}

function foo2(i: number) {
     let a: A | null = null;
     if (i) a = new A();

     if (i) a.bar(); // Error: 'a' is possibly 'null'
}

```


https://www.typescriptlang.org/docs/handbook/2/narrowing.html



More information about the Digitalmars-d mailing list