Atom Tabloları Hakkında
atom tablosu, dizeleri ve karşılık gelen tanımlayıcıları depolayan sistem tanımlı bir tablodur. Uygulama bir atom tablosuna bir dize yerleştirir ve dizeye erişmek için kullanılabilecek atomadlı 16 bitlik bir tamsayı alır. Bir atom tablosuna yerleştirilen dize, atom adı olarak adlandırılır.
Sistem bir dizi atom tablosu sağlar. Her atom tablosu farklı bir amaca hizmet eder. Örneğin, Dinamik Veri Değişimi (DDE) uygulamaları öğe-adı ve konu-adı dizelerini diğer uygulamalarla paylaşmak için genel atom tablosu kullanır. DDE uygulaması, metin dizeleri geçirmek yerine, genel atomları iş ortağı uygulamasına iletir. İş ortağı, atom tablosundan dizeleri almak için atomları kullanır.
Uygulamalar kendi öğe adı ilişkilendirmelerini depolamak için yerel atom tablolarını kullanabilir.
Sistem, uygulamalar tarafından doğrudan erişilmeyen atom tablolarını kullanır. Ancak uygulama, çeşitli işlevleri çağırırken bu atomları kullanır. Örneğin, kayıtlı pano biçimleri sistem tarafından kullanılan bir iç atom tablosunda saklanır. Uygulama, RegisterClipboardFormat işlevini kullanarak atomları bu atom tablosuna ekler. Ayrıca, kayıtlı sınıflar sistem tarafından kullanılan bir iç atom tablosunda depolanır. Uygulama, RegisterClass veya RegisterClassEx işlevini kullanarak atomları bu atom tablosuna ekler.
Bu bölümde aşağıdaki konular ele alınıyor.
- Genel Atom Tablosu
- Kullanıcı Atom Tablosu
- Yerel Atom Tabloları
- Atom Türleri
- Atom Oluşturma ve Kullanım Sayısı
- Atom-Table Sorguları
- Atom Dizesi Biçimleri
Genel Atom Tablosu
Genel atom tablosu tüm uygulamalar tarafından kullanılabilir. Bir uygulama genel atom tablosuna bir dize yerleştirdiğinde, sistem sistem genelinde benzersiz bir atom oluşturur. Atomu olan herhangi bir uygulama, genel atom tablosunu sorgulayarak tanımladığı dizeyi alabilir.
Verileri diğer uygulamalarla paylaşmak için özel bir DDE veri biçimi tanımlayan bir uygulama biçim adını genel atom tablosuna yerleştirmelidir. Bu teknik, sistem veya diğer uygulamalar tarafından tanımlanan biçimlerin adlarıyla çakışmaları önler ve iletilerin veya biçimlerin tanımlayıcılarını (atomlar) diğer uygulamaların kullanımına sunar.
Kullanıcı Atom Tablosu
Genel atom tablosuna ek olarak, kullanıcı atom tablosu da tüm işlemler arasında paylaşılan başka bir sistem atom tablosudur. Kullanıcı atom tablosu, win32k'ye yönelik az sayıda senaryo için kullanılır; örneğin, windows modülü adları, win32k'deki iyi bilinen dizeler, OLE biçimleri vb. Uygulamalar kullanıcı atom tablosuyla doğrudan etkileşim kurmasa da, kullanıcı atom tablosuna girdiler ekleyen RegisterClass , RegisterWindowMessageve RegisterClipboardFormatgibi çeşitli API'leri çağırır.
RegisterClass
tarafından eklenen girdiler UnregisterClass
tarafından silinebilir. Ancak, RegisterWindowMessage
ve RegisterClipboardFormat
tarafından eklenen girdiler oturum bitene kadar silinmez. Kullanıcı atom tablosunda daha fazla alan yoksa ve geçirilen dize tabloda yoksa, çağrı başarısız olur.
Atom Tablo Boyutu
CreateWindowdahil olmak üzere birçok kritik API kullanıcı atomlarına dayanır. Bu nedenle, kullanıcı atom tablosundaki boşluk tükenmesi ciddi sorunlara neden olur; örneğin, tüm uygulamalar başlatılamaz. Uygulamanızın atom tablolarını verimli bir şekilde kullandığından ve uygulama ile sistemin güvenilirliğini ve performansını koruduğundan emin olmak için bazı öneriler aşağıdadır:
Uygulamanızın kullanıcı atom tablosu kullanımını sınırlamanız gerekir.
RegisterClass
,RegisterWindowMessage
veyaRegisterClipboardFormat
gibi API'leri kullanarak benzersiz dizelerin depolanması, diğer uygulamalar tarafından dizeleri kullanarak pencere sınıflarını kaydetmek için genel olarak kullanılan kullanıcı atom tablosunda yer kaplar. Mümkünse, dizeleri yerel bir atom tablosunda depolamak için AddAtom /DeleteAtomkullanmanız veya atomlara çapraz işlem gerekiyorsa GlobalAddAtom /GlobalDeleteAtomkullanmanız gerekir.Kullanıcı atom tablosu sorunlarına neden olan uygulamayla ilgili bir endişe varsa, çekirdek hata ayıklayıcısını bağlayarak ve
UserAddAtomEx
çağrılarında işleme girerek kök nedeni araştırabilirsiniz (bae1 win32kbase!UserAddAtomEx /p <eprocess> "kc10;g"
). Çağrı yığınında hangi API'nin çağrıldığını görmek içinuser32!
arayın. Metodoloji, Global Atom Tablo Sızıntılarını Tanımlama bölümünde açıklanan genel atom tablosu sorun algılamasına benzer. Kullanıcı atom tablosunun içeriğini dökmenin bir diğer yolu, 0xC000 ile 0xFFFF arasındaki mümkün olan atomlar üzerinde GetClipboardFormatName işlevini çağırmaktır. Uygulama çalışırken toplam atom sayısı sürekli olarak artıyorsa veya uygulama kapatıldığında taban çizgisine geri dönmezse, bir sorun vardır.
Yerel Atom Tabloları
Bir uygulama, yalnızca uygulama içinde kullanılan çok sayıda dizeyi verimli bir şekilde yönetmek için yerel bir atom tablosu kullanabilir. Bu dizeler ve ilişkili atomlar yalnızca tabloyu oluşturan uygulama tarafından kullanılabilir.
Bir dizi yapıda aynı dizeye ihtiyaç duyan bir uygulama, yerel atom tablosu kullanarak bellek kullanımını azaltabilir. Uygulama, dizeyi her yapıya kopyalamak yerine, dizeyi atom tablosuna yerleştirebilir ve sonuçta elde edilen atomu yapılara ekleyebilir. Bu şekilde, bir dize bellekte yalnızca bir kez görünür, ancak uygulamada birçok kez kullanılabilir.
Uygulamalar, belirli bir dizeyi ararken zaman kazanmak için yerel atom tablolarını da kullanabilir. Bir arama gerçekleştirmek için bir uygulamanın yalnızca arama dizesini atom tablosuna yerleştirmesi ve sonuçta elde edilen atomu ilgili yapılardaki atomlarla karşılaştırması gerekir. Atomları karşılaştırmak genellikle dizeleri karşılaştırmaktan daha hızlıdır.
Atom tabloları karma tablolar olarak uygulanır. Varsayılan olarak, yerel bir atom tablosu karma tablosu için 37 demet kullanır. Ancak, InitAtomTable işlevini çağırarak kullanılan demet sayısını değiştirebilirsiniz. Ancak uygulama InitAtomTableçağırırsa, diğer atom yönetimi işlevlerini çağırmadan önce bunu yapması gerekir.
Atom Türleri
Uygulamalar iki tür atom oluşturabilir: dize atomları ve tamsayı atomları. Tamsayı atomlarının ve dize atomlarının değerleri çakışmaz, bu nedenle her iki atom türü de aynı kod bloğunda kullanılabilir.
Çeşitli işlevler parametre olarak dizeleri veya atomları kabul eder. Bir uygulama, atomu bu işlevlere geçirirken MAKEINTATOM makrosunu kullanarak atomu işlev tarafından kullanılabilecek bir forma dönüştürebilir.
Aşağıdaki bölümlerde atom türleri açıklanmaktadır.
Dize Atomları
Uygulamalar GlobalAddAtom, AddAtom, GlobalFindAtomve FindAtomişlevlerine null sonlandırılan dizeler geçirildiğinde, karşılığında (16 bit tamsayılar) dize atomları alır. Dize atomları aşağıdaki özelliklere sahiptir:
- Dize atomlarının değerleri, 0xC000 (MAXINTATOM) ile 0xFFFF aralığındadır.
- Bir atom tablosundaki bir atom adı için yapılan aramalarda büyük/küçük harf önemli değildir. Ayrıca, bir arama işleminde dizenin tamamı eşleşmelidir; alt dize eşleştirmesi yapılmaz.
- Bir dize atomuyla ilişkili dizenin boyutu en fazla 255 bayt olabilir. Bu sınırlama tüm atom işlevleri için geçerlidir.
- Her bir atom adıyla ilişkili bir referans sayısı vardır. Atom adı tabloya her eklendiğinde sayı artırılır ve atom adı her silindiğinde azalmış olur. Bu, aynı dize atomunun farklı kullanıcılarının birbirlerinin atom adlarını yok etmesini önler. Bir atom adının başvuru sayısı sıfıra eşit olduğunda, sistem atomu ve atom adını tablodan kaldırır.
Tamsayı Atomları
Tamsayı atomları, dize atomlarından aşağıdaki yollarla farklıdır:
- Tamsayı atomlarının değerleri, 0x0001 ile 0xBFFF (MAXINTATOM– 1) arasında değişmektedir.
- Bir tamsayı atomunun dize gösterimi #ddddşeklindedir; burada dddd tarafından temsil edilen değerler ondalık basamaklardır. Baştaki sıfırlar yoksayılır.
- Bir tamsayı atomuyla ilişkili referans sayısı veya depolama yükü bulunmamaktadır.
Atom Oluşturma ve Kullanım Sayısı
Uygulama, AddAtom işlevini çağırarak yerel bir atom oluşturur; GlobalAddAtom işlevini çağırarak genel bir atom oluşturur. Her iki işlevin de bir dizeye işaret eden bir işaretçiye ihtiyacı vardır. Sistem, dize için uygun atom tablosunu arar ve uygulamaya karşılık gelen atomu döndürür. Bir dize atomu söz konusu olduğunda, dize atom tablosunda zaten bulunuyorsa, sistem bu işlem sırasında dize için başvuru sayısını artırır.
Aynı atom adını eklemek için yapılan yinelenen çağrılar aynı atomu döndürür. AddAtom çağrıldığında tabloda atom adı yoksa, atom adı tabloya eklenir ve yeni bir atom döndürülür. Bu bir dize atomuysa, referans sayısı da bire ayarlanır.
Bir uygulamanın artık yerel atom kullanması gerekmediğinde DeleteAtom işlevini çağırması gerekir; artık bir genel atom gerekmediğinde GlobalDeleteAtom işlevini çağırması gerekir. Bir dize atomu söz konusu olduğunda, bu işlevlerden biri ilgili atomun başvuru sayısını bir azaltır. Referans sayısı sıfıra ulaştığında, sistem tablodan atom adını siler.
Bir atom dizisinin adı, başvuru sayısı sıfırdan büyük olduğu sürece, onu tabloya yerleştiren uygulama sonlandırılsa bile genel atom tablosunda kalır. Tablodaki atomların başvuru sayılarından bağımsız olarak, ilişkili uygulama sonlandırıldığında yerel bir atom tablosu yok edilir.
Atom-Table Sorguları
Uygulama, FindAtom veya GlobalFindAtom işlevini kullanarak belirli bir dizenin zaten atom tablosunda olup olmadığını belirleyebilir. Bu işlevler, bir atom tablosunda belirtilen dizeyi arar ve dize varsa ilgili atomu döndürür.
Uygulama, aranan dizeye karşılık gelen atoma sahip olması koşuluyla, bir atom tablosundan atom adı dizesi almak için GetAtomNameveya GlobalGetAtomNameişlevinikullanabilir. Her iki işlev de belirtilen atomun atom adı dizesini arabelleğe kopyalar ve kopyalanan dizenin uzunluğunu döndürür. GetAtomName yerel atom tablosundan bir atom adı dizesi alır ve GlobalGetAtomName genel atom tablosundan bir atom adı dizesi alır.
Atom Dizesi Biçimleri
AddAtom, GlobalAddAtom, FindAtomve GlobalFindAtom işlevleri null olarak sonlandırılan bir dizeye işaretçi alır. Bir uygulama bu işaretçiyi aşağıdaki yollardan biriyle belirtebilir.
Dize biçimi | Açıklama |
---|---|
# dddd | Ondalık sayı dizesi olarak belirtilen tamsayı. Tamsayı atomu oluşturmak veya bulmak için kullanılır. |
dize atom adı | Bir dize atom adı. Bir atom tablosuna bir dize atom adı eklemek ve karşılığında bir atom almak için kullanılır. |