Daftar perubahan dalam D 2.092. Meminjam Meminjam

Dari penerjemah. Saya biasanya tidak menerjemahkan artikel seperti itu, karena saya tidak melihat sesuatu yang menarik di dalamnya. Di sini, dua inovasi kecil, tetapi yang paling penting - dukungan untuk menghubungkan langsung perpustakaan C ++ dan sistem "pinjaman" kepemilikan dan pinjaman dari Rust (yang kedua adalah menelan DFA, yang pertama keluar di GCC10 hanya beberapa hari yang lalu, dan Nim juga berpikir tentang hal itu dengan deskripsi). Sebenarnya, saya tidak menerjemahkan daftar yang membosankan, dan tautannya mengarah ke yang asli.

Versi sebelumnya dari daftar 2.0.91.1 (ind)
Tempat untuk mengunduh

2.092.0 keluar dengan 15 perubahan penting dan 44 perbaikan bug dan peningkatan. Terima kasih banyak kepada 47 kontributor yang memungkinkan rilis ini.

Perubahan kompiler


  1. The -revert = import dan -transition = checkimport switch baris perintah dihapus
  2. Menambahkan dukungan untuk pengkodean (penyusunan) nama C ++ GNU ABI
  3. Konstruktor dan destruktor untuk modul yang bukan eksternal (D) ditandai sudah usang
  4. Pelanggaran DIP25 Ditandai Secara Default Usang
  5. Kepemilikan Prototipe dan Sistem Pinjaman untuk Pointer
  6. Ditambahkan = -preview di pilihan itu ternyata kelas penyimpanan di dalam lingkup const
  7. Parameter printf dan scanf sekarang diperiksa untuk kesesuaian dengan penentu format
  8. Variabel lingkungan SOURCE_DATE_EPOCH sekarang didukung.

Perubahan runtime


  1. TypeInfo_Class/TypeInfo_Interface.isBaseOf C#/Java isAssignableFrom
  2. core.memory.pageSize minimumPageSize


  1. Date.isoWeekYear Date.fromISOWeek std.datetime.date
  2. std.xml
  3. std.digest.digest

Dub


  1. Dub lint --report-file

Daftar lengkap perbaikan dan peningkatan (bahasa Inggris)

Prim.per.U mengecewakan saya, karena tidak mungkin untuk mengatur konten yang benar dari tautan dalam-halaman ke pengungkapan, seperti dalam aslinya, sorry = (

Perubahan kompiler


  1. Perintah baris switch -revert = import dan -transition = checkimport telah dihapus.

    Kunci-kunci ini tidak melakukan apa-apa, dan untuk beberapa waktu mereka ditandai usang. Kompiler tidak akan lagi mengenalinya.
  2. () C++ GNU ABI

    GNU ABI C++11 GCC 5.1. D C++, DMD UDA ( ) gnuAbiTag, core.attribute object ( ). ABI , , ++ . , std::string C++11 (DMD -extern-std={c++11,c++14,c++17}).

    :

    extern(C++):
    @gnuAbiTag("tagOnStruct")
    struct MyStruct {}
    @gnuAbiTag("Multiple", "Tags", "On", "Function")
    MyStruct func();

    gnuAbiTag. ( ). UDA -extern-std=c++11. (-extern-std=c++98) UDA . UDA extern(C++) .
  3. , extern(D) .

    ( ) , extern(D), . , , / , , 479, 479, .

    , , .
  4. DIP25 .

    DIP25 2.067.0, , -preview=dip25. , , DIP1000.

    , , -preview=dip25, -preview=dip25. ( ).

    DIP25 , @ safe . , ref , return , .

    struct Foo
    {
        int x;
        // returning `this.x` escapes a reference to parameter `this`, perhaps annotate with `return`
        ref int method() /* return */ { return this.x; }
    }
    // returning `v` escapes a reference to parameter `v`, perhaps annotate with `return`
    ref int identity(/* return */ ref int v) { return v; }

    return . DIP25 .
  5. -preview=in in scope const.

    const scope, in . , in (. inout ) .

    -preview=in, :

    void fun(in int x);
    void fun(const int x);

    -preview=in, :

    void fun(in int x);
    void fun(scope const int x);
  6. printf scanf

    C99 7.19.6.1 printf 7.19.6.2 scanf.

    printf , . , .

    scanf .

    :

    1. ,
    2. ,
    3. — , s
    4. C99

    -, .

    .

    , printf/scanf, :

    printf("%k\n", value);  // error: non-Standard format k
    const format = "%k\n";
    printf(format.ptr, value);  // no error

    — . ,

    string s;
    printf("%.*s\n", s.length, s.ptr);
    printf("%d\n", s.sizeof);
    ulong u;
    scanf("%lld%*c\n", &u);

    :

    string s;
    printf("%.*s\n", cast(int) s.length, s.ptr);
    printf("%zd\n", s.sizeof);
    ulong u;
    scanf("%llu%*c\n", &u);

    printf scanf pragma(printf) printf pragma(scanf) scanf.

    , :

    1. extern (C ) extern (C++)
    2. const(char)*
    3. … -v , va_list ( «v» printf scanf)
    .

    «v»- .
  7. SOURCE_DATE_EPOCH

    SOURCE_DATE_EPOCH. UNIX ( 1970-01-01 00:00:00), . DMD __DATE__, __TIME__ __TIMESTAMP__ .



Sistem kepemilikan / pinjaman (juga dikenal sebagai OB) untuk pointer memastikan bahwa pointer dereferenced menunjuk ke objek memori yang valid.

Lingkup sistem OB prototipe


Ini adalah prototipe sistem OB, diadaptasi untuk D. Awalnya, ini dimaksudkan hanya untuk pointer, dan bukan untuk array dinamis, referensi kelas, referensi atau bidang penunjuk dalam agregat. Menambahkan dukungan semacam ini akan mempersulit implementasi, tetapi tidak mengubah esensinya, karena itu ditunda untuk nanti. Objek RAII dapat dengan aman mengatur ingatannya sendiri, sehingga tidak tercakup oleh OB. Terlepas dari metode, apakah pointer mengalokasikan memori menggunakan GC atau pengalokasi lainnya, ini tidak penting untuk OB, mereka tidak berbeda dan diproses secara identik.

Sistem OB hanya aktif dalam fungsi yang dijelaskan dengan atribut @ live. Ini diterapkan setelah pemrosesan semantik semata-mata sebagai pemeriksaan atas pelanggaran aturan zat organik. Sintaks baru tidak ditambahkan. Tidak ada perubahan yang dilakukan pada kode yang dihasilkan. Jika @ hidup fungsi memanggil fungsi-fungsi lain selain @ hidup , diharapkan fungsi-fungsi yang disebut akan menjadi @ live- interface yang kompatibel, meskipun tidak diuji. Jika fungsi-fungsi non- live memanggil fungsi-fungsi @ live , argumen yang diberikan diharapkan untuk mengikuti konvensi @ live .

Sistem OB mendeteksi kesalahan:

  • pointer dereferencing yang dalam keadaan tidak valid
  • lebih dari satu pointer aktif ke objek memori yang bermutasi.

Itu tidak akan mendeteksi upaya untuk melakukan referensi pointer nol atau, berpotensi, pointer nol. Ini tidak berfungsi, karena saat ini tidak ada metode untuk menganotasi tipe sebagai pointer yang tidak dapat dibatalkan.

Prinsip dasar OB


Desain OB mengikuti dari prinsip berikut:

Untuk setiap objek memori, dapat ada tepat satu pointer bermutasi, atau beberapa pointer non-mutasi (hanya baca).

Rancangan


Pointer bermutasi tunggal disebut "pemilik" objek memori. Dia secara transitif memiliki objek memori dan semua objek dalam memori dapat diakses darinya (yaitu grafik objek). Karena itu adalah satu-satunya penunjuk ke objek memori ini, ia dapat dengan aman mengelola memori (mengubah bentuk, mengalokasikan, membebaskan, dan mengubah ukuran) tanpa mengetuk tanah di bawah kaki pointer lainnya (bermutasi atau tidak) yang mungkin ada di dalamnya (grafik memori) menunjukkan.

Jika ada beberapa petunjuk ke grafik objek memori yang hanya-baca, mereka dapat dengan aman membaca darinya tanpa khawatir tentang perubahan mendadak pada grafik objek dalam memori.

Detail teknologi lainnya berkaitan dengan bagaimana pointer menjadi read-only dan tidak valid, dan bagaimana Prinsip Inti OB dipertahankan secara konstan.

Pointer terlacak
Hanya pointer yang dideklarasikan dalam fungsi @ live karena hal ini , parameter fungsi, atau variabel lokal dilacak . Variabel dari fungsi lain tidak dilacak, bahkan @ live , karena analisis interaksi dengan fungsi lain sepenuhnya hanya bergantung pada tanda tangan dari fungsi ini, dan bukan pada internalnya. Parameter yang merupakan const tidak dilacak.

Status
pointer Setiap pointer berada di salah satu status berikut: Tidak

terdefinisi
Pointer dalam keadaan tidak valid. Mendereferensi pointer seperti itu adalah kesalahan.
Pemilik
Pemilik adalah satu-satunya penunjuk ke grafik objek dalam memori. Biasanya sebuah pointer - Pemilik tidak memiliki atribut lingkup . Jika pointer dengan atribut scope diinisialisasi dengan ekspresi yang tidak diturunkan dari pointer yang dilacak, maka itu menjadi Pemilik.
Jika pointer Pemilik ditugaskan ke pointer lain - Pemilik, maka yang pertama masuk ke status Tidak terdefinisi.
Dipinjam
Pointer pinjaman adalah pointer yang sementara menjadi satu-satunya pointer ke grafik objek memori. Dia masuk ke negara ini melalui penugasan dari penunjuk - Pemilik, sedangkan Pemilik masuk ke negara Peminjam sampai penggunaan penunjuk pinjaman selesai.
Pointer yang dipinjam harus memiliki atribut scope dan menjadi pointer ke objek yang bisa berubah.
Read
-Only Indeks Read- Only ditugaskan oleh Pemilik. Selama pointer Read-Only masih hidup, hanya pointer Read-Only yang masih dapat ditetapkan dari Pemilik ini. Pointer baca-saja harus memiliki atribut lingkup , dan itu juga harus tidak menjadi pointer ke objek yang bisa berubah.

Seumur hidup

Masa pakai dari indikator "Borrowed" atau "Read-only" dimulai dari saat pertama kali direferensikan (dan bukan sejak saat itu diinisialisasi atau diberi nilai) dan berakhir ketika nilai tersebut direferensikan terakhir.

Ia juga dikenal sebagai Lifetimes Non-Lexical . Status

transisi untuk pointer

Suatu pointer mengubah statusnya ketika salah satu dari operasi ini dilakukan:

  • memori dialokasikan untuk itu (misalnya, variabel lokal di stack), yang menempatkan pointer dalam keadaan tidak terdefinisi
  • inisialisasi (dianggap sebagai penugasan)
  • penugasan - sumber dan target pointer berubah status tergantung pada keadaan apa mereka berada, serta pada tipe dan kelas penyimpanan mereka
  • out ( ), , .
  • ref , , .
  • , .
  • - ()
  • , , .
  • , ,
  • , ,
  • ,


Menjadi prototipe, ada banyak aspek yang belum dipertimbangkan, dan tidak akan sampai prototipe menunjukkan bahwa ini adalah solusi yang bisa diterapkan.

Kesalahan

Berharap banyak kesalahan. Silakan laporkan ke bugzilla dan beri tag dengan kata kunci "ob". Tidak perlu melaporkan batasan lain yang sudah terdaftar di sini.

Referensi ke kelas dan array asosiatif tidak dilacak.
Diasumsikan bahwa mereka dikendalikan oleh GC.

Meminjam dan membaca dari bukan pemilik

Pemilik dimonitor karena kebocoran, tetapi tidak untuk indikator lainnya. Peminjam dianggap Pemilik jika mereka tidak diinisialisasi dengan sebuah pointer.

@live void uhoh()
{
    scope p = malloc();  // p is considered an Owner
    scope const pc = malloc(); // pc is not considered an Owner
} // dangling pointer pc is not detected on exit

Tampaknya tidak masuk akal untuk menandai pointer seperti ruang lingkup , mungkin ini dapat diperbaiki dengan memperlakukan ini sebagai kesalahan.

Pointer dibaca / ditulis oleh fungsi bersarang,
tidak dilacak.

@live void ohno()
{
    auto p = malloc();

    void sneaky() { free(p); }

    sneaky();
    free(p);  // double free not detected
}



Analisis Pengecualian mengasumsikan bahwa pengecualian tidak dibuang.

@live void leaky()
{
    auto p = malloc();
    pitcher();  // throws exception, p leaks
    free(p);
}

Salah satu solusinya adalah dengan menggunakan scope (keluar) :

@live void waterTight()
{
    auto p = malloc();
    scope(exit) free(p);
    pitcher();
}

baik menggunakan objek RAII atau hanya memanggil fungsi nothrow.

Parameter malas

Tidak diperhitungkan.

Kompleksitas kuadrat

Analisis ini menunjukkan kompleksitas kuadrat, cobalah untuk menjaga fungsi @ live tetap kecil.

Mencampur berbagai kelompok memori

Menggabungkan kumpulan memori yang berbeda:

void* xmalloc(size_t);
void xfree(void*);

void* ymalloc(size_t);
void yfree(void*);

auto p = xmalloc(20);
yfree(p);  // should call xfree() instead

tidak terdeteksi.

Ini dapat dielakkan dengan menggunakan kumpulan khusus untuk jenis tertentu:

U* umalloc();
void ufree(U*);

V* vmalloc();
void vfree(V*);

auto p = umalloc();
vfree(p);  // type mismatch

dan mungkin melarang konversi implisit untuk membatalkan * di fungsi @ live .

Argumen fungsi variadic

Argumen ke fungsi variadic (misalnya, printf) dianggap dikonsumsi. Meskipun ini aman, tampaknya tidak terlalu praktis dan kemungkinan akan membutuhkan peninjauan.

Perubahan runtime


  1. TypeInfo_Class/TypeInfo_Interface.isBaseOf C#/Java isAssignableFrom.

    TypeInfo_Class.isBaseOf true, , , , . isBaseOf, isAssignableFrom, , opAssign D — . TypeInfo_Interface.isBaseOf , TypeInfo_Class, TypeInfo_Interface.
  2. core.memory.pageSize minimumPageSize.

    pageSize .

    import core.memory : pageSize;
    ubyte[] buffer = new ubyte[pageSize];

    minimumPageSize .

    , . , . pageSize, .

    , , , : ubyte[minimumPageSize].

    import core.memory : minimumPageSize;
    ubyte[minimumPageSize] buffer;



  1. Date.isoWeekYear Date.fromISOWeek std.datetime.date

    ISO 8601 , Date and DateTime.

    ISO , . Date.fromISOWeek(2020, 11, DayOfWeek.mon) Date(2020, 3, 9).

    ISO , () .isoWeekYear Date ISO. , .isoWeekAndYear , .
  2. std.xml .

    std.xml . , , UndeaD. xml dub- dxml.
  3. std.digest.digest .

    2.076.1 . std.digest .

    std.digest.digest 2.101.

Dub


  1. .

    Posix , .dub. dub (, .swap.file.d), . , dub . , dub.

    , .
  2. Dub lint --report-file.

    Dub lint --report-file: dub lint --report-file report.json

All Articles