pillinetwork hesabınızla giriş yapın.

T.C. Kimlik No Algoritması

Bir müşteriden inatla gelen doğrulama isteği üzerine T.C. kimlik no'sunun rakamsal olarak "kesinlikle" doğru olmadan formun validate etmemesi için ufak bir araştıma sonucunda şunu buldum.

TC Kimlik numaraları 11 basamaktan oluşmaktadır. İlk 9 basamak arasında kurulan bir algoritma bize 10. basmağı, ilk 10 basamak arasında kurulan algoritma ise bize 11. basamağı verir.
* 11 hanelidir.
* Her hanesi rakamsal değer içerir.
* İlk hane 0 olamaz.
* 1. 3. 5. 7. ve 9. hanelerin toplamının 7 katından, 2. 4. 6. ve 8. hanelerin toplamı çıkartıldığında, elde edilen sonucun 10'a bölümünden kalan, yani Mod10'u bize 10. haneyi verir.
* 1. 2. 3. 4. 5. 6. 7. 8. 9. ve 10. hanelerin toplamından elde edilen sonucun 10'a bölümünden kalan, yani Mod10'u bize 11. haneyi verir.

Kaynak

Birkaç link ötesinde de şu kodlara rastladım

C#

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
public static bool TcDogrulaV2(string tcKimlikNo)
{
bool returnvalue = false;
if (tcKimlikNo.Length == 11)
{
Int64 ATCNO, BTCNO, TcNo;
long C1,C2,C3, C4, C5,C6,C7,C8, C9,Q1,Q2;
TcNo = Int64.Parse(tcKimlikNo);
ATCNO = TcNo / 100;
BTCNO = TcNo / 100;
C1 = ATCNO % 10; ATCNO = ATCNO / 10 ;
C2 = ATCNO % 10; ATCNO = ATCNO / 10 ;
C3 = ATCNO % 10; ATCNO = ATCNO / 10 ;
C4 = ATCNO % 10; ATCNO = ATCNO / 10 ;
C5 = ATCNO % 10; ATCNO = ATCNO / 10 ;
C6 = ATCNO % 10; ATCNO = ATCNO / 10 ;
C7 = ATCNO % 10; ATCNO = ATCNO / 10 ;
C8 = ATCNO % 10; ATCNO = ATCNO / 10 ;
C9 = ATCNO % 10; ATCNO = ATCNO / 10 ;
Q1 = ((10-((((C1+C3+C5+C7+C9)*3)+(C2+C4+C6+C8))%10))%10);
Q2 = ((10-(((((C2+C4+C6+C8)+Q1)*3)+(C1+C3+C5+C7+C9))%10))%10);
returnvalue = ((BTCNO * 100)+(Q1 * 10)+Q2 == TcNo);
}
return returnvalue;
}

VB

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
Public Shared Function TcDogrulaV2(ByVal tcKimlikNo As String) As Boolean
Dim returnvalue As Boolean = False
If (tcKimlikNo.Length <> 11) Then
Return returnvalue
End If
Dim TcNo As Long = Long.Parse(tcKimlikNo)
Dim ATCNO As Long = (TcNo / 100)
Dim BTCNO As Long = (TcNo / 100)
Dim C1 As Long = (ATCNO Mod 10)
ATCNO = (ATCNO / 10)
Dim C2 As Long = (ATCNO Mod 10)
ATCNO = (ATCNO / 10)
Dim C3 As Long = (ATCNO Mod 10)
ATCNO = (ATCNO / 10)
Dim C4 As Long = (ATCNO Mod 10)
ATCNO = (ATCNO / 10)
Dim C5 As Long = (ATCNO Mod 10)
ATCNO = (ATCNO / 10)
Dim C6 As Long = (ATCNO Mod 10)
ATCNO = (ATCNO / 10)
Dim C7 As Long = (ATCNO Mod 10)
ATCNO = (ATCNO / 10)
Dim C8 As Long = (ATCNO Mod 10)
ATCNO = (ATCNO / 10)
Dim C9 As Long = (ATCNO Mod 10)
ATCNO = (ATCNO / 10)
Dim Q1 As Long =((10-(((((((C1+C3)+C5)+C7)+C9)*3)+(((C2+C4)+C6)+C8))Mod 10))Mod 10)
Dim Q2 As Long =((10-(((((((C2+C4)+C6)+C8)+Q1)*3)+((((C1+C3)+C5)+C7)+C9))Mod 10))Mod 10)
Return ((((BTCNO * 100) + (Q1 * 10)) + Q2) = TcNo)
End Function

Kaynak


VB kodlarını kullanmak istedim ancak rakamları string olarak algılamak gibi garip bir hata ile karşılaştım. zaten yukarıda alıntı olarak belirttiğim doğrulama kurallarından farklı hata mesajları almak istediğimden VB kod üzerinde oynamalar yaparak şu hale getirdim. TcDogrulaV2 ve isNumeric (js) fonksiyonlarını kullanarak olumlu sonuç almış bulunmaktayım.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
Function TcDogrulaV2(ByVal tcKimlikNo As String) As Boolean
Dim returnvalue As Boolean = False
If (tcKimlikNo.Length <> 11) Then
tcCustom.ErrorMessage = "<br />TC Kimlik Numarası 11 Haneli Olmalıdır."
Return returnvalue
End If
Dim TcNo As Long = Long.Parse(tcKimlikNo)
Dim BTCNO As Long = Long.Parse(Left(tcKimlikNo, 9))
Dim C1 As Long = Long.Parse(Mid(tcKimlikNo, 1, 1))
Dim C2 As Long = Long.Parse(Mid(tcKimlikNo, 2, 1))
Dim C3 As Long = Long.Parse(Mid(tcKimlikNo, 3, 1))
Dim C4 As Long = Long.Parse(Mid(tcKimlikNo, 4, 1))
Dim C5 As Long = Long.Parse(Mid(tcKimlikNo, 5, 1))
Dim C6 As Long = Long.Parse(Mid(tcKimlikNo, 6, 1))
Dim C7 As Long = Long.Parse(Mid(tcKimlikNo, 7, 1))
Dim C8 As Long = Long.Parse(Mid(tcKimlikNo, 8, 1))
Dim C9 As Long = Long.Parse(Mid(tcKimlikNo, 9, 1))
Dim Q1 As Long = ((10 - (((((((C1 + C3) + C5) + C7) + C9) * 3) + (((C2 + C4) + C6) + C8)) Mod 10)) Mod 10)
Dim Q2 As Long = ((10 - (((((((C2 + C4) + C6) + C8) + Q1) * 3) + ((((C1 + C3) + C5) + C7) + C9)) Mod 10)) Mod 10)
'Response.Write((((BTCNO * 100) + (Q1 * 10)) + Q2) & " - ")
'Response.Write(tcKimlikNo)
If ((((BTCNO * 100) + (Q1 * 10)) + Q2) = TcNo) Then
tcCustom.ErrorMessage = ""
Else
tcCustom.ErrorMessage = "<br />Hatalı TC Kimlik Numarası."
End If
Return ((((BTCNO * 100) + (Q1 * 10)) + Q2) = TcNo)
End Function

Arada ismi geçti bari atlamayayım dedim.

1
2
3
4
5
6
7
8
9
10
11
var isShift=false;
function keyUP(keyCode)
{
if(keyCode==16) isShift = false;
}
function isNumeric(keyCode)
{
if(keyCode==16) isShift = true;
return ((keyCode >= 48 && keyCode <= 57 || keyCode == 8 || (keyCode >= 96 && keyCode <= 105)) && isShift == false);
}

/* golduck yazdı. 12 Eylül 2009 10:30. 43 yorum var */

Yorumlar

Harika bir bilgi, teşekkürler.

/* /\kC */

buyrun. bu da tarafımdan javascripte çevrilmiş hali.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
function check_tcno(a){
if(a.substr(0,1)==0&&a.lenght!=11){
return false;
}
var i = 9, md='', mc='', digit, mr='';
while(digit = a.charAt(--i)){
i%2==0 ? md += digit : mc += digit;
}
if(((eval(md.split('').join('+'))*7)-eval(mc.split('').join('+')))%10!=parseInt(a.substr(9,1),10)){
return false;
}
for (c=0;c<=9;c++){
mr += a.charAt(c);
}
if(eval(mr.split('').join('+'))%10!=parseInt(a.substr(10,1),10)){
return false;
}
return true;
}

Bu da benden PHP+RegExp hali:

1
2
3
4
function check_tcno($tcno) {
preg_replace('/([1-9]{1})([0-9]{1})([0-9]{1})([0-9]{1})([0-9]{1})([0-9]{1})([0-9]{1})([0-9]{1})([0-9]{1}).*$/e', "eval('\$on=((((\\1+\\3+\\5+\\7+\\9)*7)-(\\2+\\4+\\6+\\8))%10); \$onbir=(\\1+\\2+\\3+\\4+\\5+\\6+\\7+\\8+\\9+\$on)%10; \$sonIki = \$on.\$onbir;')", $tcno);
return(substr($tcno, -2) == $sonIki);
}

tuttu :)

/* http://protestit.org/ */

way tuncay hll olsun
adam sak die regex yazmis ya :) yuh

PHP olmasa satır satır kod yazacaktım. RegExp PHP ile güzel ;)

regex süper bişey zaten :D

/* / oguzozcan.com / */

koda şunun için bir ekleme yapsanız iyi olacak:
ilk 9 rakamı birbirine eşit ve son 2 rakamı 0 olan Tc. Kimlik No'lar kabul edilmemelidir.

Not: Eğer çoklu üyelikleri engelleme amaçlı kimlik no gibi bir aracı kullanmak istiyorsanız, size tavsiyem hiç denememeniz. Ben denedim. Hata ettim.

tc kimlik no ile üniversite öğrencisi olup olmadığı devletin verdiği kpss hizmetiyle öğrenilebiliyor. bu hizmetten yararlanmak için şirket olmalısın (şahıs şirketi hariç). Ayrıca bu hizmete bağlanacağın statik bir ip belirtmelisin.

mantığı anladım, php ile kendi aile fertlerimi ileri geri nasıl bulabileceğimi de buldum...

gel gelelim test edip, bu kimlik id sinin kime ait olduğunu bulacağım bir sayfa bulamadım...

yine de güzel bir şeydi... aklımdan, bu sistem de kırılır diye geçiyordu...

/* kitaphaber, kitap ve eleştiri kaynağınız. */

Üstte 7 katı dediği yer sanırım 3 katı olacak.

Yok doğru olan 7 katı. ama burda farklı bir yol izlenmiş. Direkt formul bu şekilde. Kendi projemde de bu şekilde düzenlemiştim.

Q1 = ((c1+c3+c5+c7+c9)*7 - (c2+c4+c6+c8)) Mod 10
Q2 = ((c1+c2+c3+c4+c5+c6+c7+c8+c9+Q1) Mod 10

Yukarıda anlatılanlar kaynaklara dayalı anlatımdı.

TC kimlik numaram algoritmaya uymuyor

/* Listeniz.Net CEO Of Sharp */

yeterince test yapmamış olsam tamam derdim ama. 20 Numaradan 20 side geçince testten. doğruluğuna inanıyorsun...

golduck'ın algoritmasında sorun yok. denedim, çalışıyor.

Peki bu hash nasıl bulundu? Birilileri deneme yanılma yoluyla mı buldular yoksa bilimsel yollar mı izlendi? Yoksa devlet mi yayınladı? Ya da bunu yapanlar arkadaşlarını falan mı söylediler?

Ben bi hash'ı çözmek istiyorum da.

1-) Bunu yapanlarda yazılımcılar. Yazılımcı bir arkadaşına söyler, o bir başkasına vs. vs. uzar gider, buralara kadar gelir...
2-) Ayrıca bu işin sanatını bilen şifre kırıcılar var. Onlarda çözmüş olabilir.

/* / oguzozcan.com / */

Bu kadar saçma bir algoritma olamaz. Sözüm yukarıda algoritmayı yazan arkadaşlara değil, TC kimlik numarasının son iki hanesinin ilk dokuz hanesine matematiksel olarak bağlı olması saçmalık. Son iki veya üç hanenin rastgele seçilmiş olması gerekirdi. Şu haliyle basit bir döngü yardımıyla bir sürü gerçek TC Kimlik numarası üretilebilir. Oysa dediğim gibi son 3 hane rastgele seçilmiş olsaydı, üretilen herhangi bir numaranın gerçek olması ihtimali binde bir olurdu.

Tabi rastgele üretilseydi de kontrol yapılması gerekince kimse kontrol edemeseydi doğru yanlış mı asla bilemeseydik. Güzel mantık.

peki ilk 9 hanenin üretimindeki algoritmayla ilgili fikri bilgisi olan var mı ? Yoksa o kısım tamamen rasgele mi üretiliyor?

Formülleri incelerken TC Kimlik Numarasının son 2 hanesinin sadece doğrulama amaçlı olarak orada olduğuna değinmiştim. O nedenle 11 basamaklı TC Kimlik Numarasının son 2 hanesini attığımda geriye kalır sağdan 9 basamaklı başka bir sayı kaldı. Bu sayıdan 29999 çıkarttığımda kütükte benden 1 önceki birey numarasına sahip olan kişinin TC Kimlik Numarasının ilk 9 basamağını bulmuştum. Yine o sayıdan da 29999 çıkardığımda ondan bir önceki kişinin TC Kimlik Numarasının ilk 9 basamaklı sayısını bulmuştum.
...
...

İşin özeti şu; TC Kimlik Numaraları her ne kadar sıralı gözükmese de aslında birey bazında ardışık. Tek fark, sayının 1'er 1'er değil, 29999'ar 29999'ar artıyor olması...

Kaynak

Super! Keske dogrulama öncesi kesfetseydik =)

sohbet süper olmuş, katkıda bulunan dostlara teşekkür ederim.

Makale sahibi demiş ki;

VB kodlarını kullanmak istedim ancak rakamları string olarak algılamak gibi garip bir hata ile karşılaştım.

garipliği önce kendinizde aramalısınız! nitekim;

Function TcDogrulaV2(ByVal tcKimlikNo As String) As Boolean

tcKimlikNo isimli parametre zaten string olarak yakalanmış, string olarak algılamasaydı esas gariplik o zaman yaşanırdı. altını çizdiğim ifadeyi integer olarak değiştirseydiniz başka başka gereksiz fonksiyonlar kullanmanız gerekmez visual basic için garip betimlemesi yapma ihtiyacınız da kalmazdı.

/* if life="" then call BatsinBuDunya() */

@lazaronnie

düzelttiğin için teşekkür ederim arkadaşım. Ama sorunu kendimde arayamıyorum malesef. Çünkü "rakamları string olarak algılamak gibi garip bir hata ile karşılaştım." derken ilk belirttiğim vb kodu, yani bana ait olmayan kod içerisinde toplama işlemi yapıldığında string değer veriyordu. (1+3 = 4 yerine 1 + 3 = 13 gibi). bu kodu yazan arkadaşın bilgisini göz önüne aldığımda bu hata ile karşılaşmam evet garip geldi.(ki .net kullanmakta gerçekten yeniyim) ben de kendi kodumda o sorunu giderdim ve sunumumu yaptım.

Neyse dikkatin için tekrar teşekkür ederim.

Sert çıktıysam özür dilerim, .net'te yeni olduğunuzu bilmiyordum..

/* if life="" then call BatsinBuDunya() */

bilgiler süper makaleyi yazana ve bize ulaştırana teşekkürler ;)

güzel makale tuttum seni dostum

bu algoritmayı beğenmeyen sevgili arkadaşlar, sizce nasıl bir algoritma yazılabilirdi. Algoritma konusunda iyi değilim, ancak merak ettim. Fikirlerinizi bir alıyım dedim.

@darkhorn, @moratmoon
Sahip olduğun bir kredi kartının numarasının ilk 12 rakamı sıralı bir sayının rakamları olsa, geriye kalan rakamlar bu sıralı sayılara istinaden belli bir algoritma ile üretilen rakamlar olsa, bu algoritmanın ne olduğu da bilinse, kredi kartı kullanmaya devam eder miydin?

İşte bu yüzden son iki rakamın diğerlerine bağlı olmasının saçma olduğunu savunuyorum.

@algorian, amaç numarayı gizlemek, şifrelemek değil. amaç numaranın yanlış yazılmasını önlemek. örnek vereyim. kendimden örnek vereyim, ben öğrenciyim, öğrenci numaram da 1234567 gibi 7 basamaklı bişey. son rakamı ilk 6 rakamına göre oluşturuluyor. her ay yurt parasını yatırmaya gidiyorum, numaramı söylüyorum öyle ödeniyor, aşağı yukarı 5-10 ödemeden birinde göevli numarayı yanlış algılıyor. düşün ki 123456 olsaydı öğrenci numarası, başkasının yurt ücretini ben ödeyecektim. onun önüne geçmek için 7. haneyi oluşturmuşlar. o yüzden numarada yanlış olduğunda ödemeyi yapamıyor banka görevlisi. aynı şey tc kimlik numarası için de geçerli. eğer o sondaki 2 numara olmasa kaç kişinin başı yanardı haberin var mı?
öğrenci numaraları şöyle gidiyor:
1234564
1234571
1234588
1234598
1234609
1234614

Kredi kartı örneği çok yersiz olmuş, kredi kartı numarası bilsen bile kredi kartı sahibinin adını soyadını, hangi kart türü olduğunu, son kullanma tarihini ve cvc numarasını bilmen gerekir. ikincisi o kredi kartı numarasının son iki rakamı bir algoritmaya göre oluşturulsa son iki rakamını bilmen için ilk 10 rakamını bilmen nerekecek, kim nerden bilecek ki onu?

bir de tc kimlik numarasının bilinmesi çok da zararlı değil, kim ne yapabilirki tc kimlik numarasıyla? her tc kimlik numarasını gösterene sanki kredi kartı veriyorlar. onun için adını soyadını, doğum yeri tarihi, adresi falanı filanı bilmen lazım ki sahtekarlık yapabilesin... ki onu da nerden öğreneceksin, kaldı ki ilk hash'i değil de ilk rakamları nerden öğrenecen.

yani şimdi diyoum ki, sen bu algoritmayı biliyorsun, ne yapabilirsin ki? gidip biisinin kimliğine bakıp ilk 9 hanesini mi alacaksın? sonra da son iki hanesini mi hesaplayaca? e bakmışken son iki hanesine de bak artık.

yoksa kafana göre bir numara sallayıp tc kimlik numarasının tamamını mı bulacaksın? buldun, ne yapabilirsin ki o numarayla, kime ait olduğunu nereden bileceksin? ragele bir şahsiyet oluşturup hesap mı açcaksın? rasgele bir kimlik oluşturdun diyelim, bankalar içişlerinin veritabanına bağlanıyorlar kimliği kontrol etmek için, yakayı ele vereceksin.

yani bana nasıl süistimal edilebileceğini söyle sana nasıl yanıldığını söyleyeyim.

@darkhorn bazı sitelere üye olurken tckimlik numaranın sayısal değerine göre üyeliği kabul ediyor. O sitelere kendi tc kimlik numaranı vermek istemiyorsan bu algoritmaya göre oluştur bi tckimlik onunla gir :) bununda hiçbir zararı yok.

teşekkürler

/* NcGsoFtwarE */

Key odemeleri aciklanirken verilen isim ve TC kimlik numaralari ile buyuk bir dolandiricilik yapildimi bakmak lazim.

@shibbytr bazı siteler de başvuru yaparak nüfus kütüklerine sayısal erişim izni alıyorlar.

Sizi üye yaparken isim soyisim falan sormuyorlar. Direk tc nosu istiyorlar. Ajax yardımıyla nüfus kütüklerinden isminizi çekebiliyorlar bu şekilde. Eğer böyle bir siteye aynı anda tc ve isim soran uygulama eklenirse verdiğiniz tc nosuna yanıt olarak dönen isim bilgisiyle sizin verdiğiniz bilgi birbirini tutmaz ise web siteleri size ait olmayan bir tc nosunu girdiğinizi anlayabilecektir.

Kırılmaz diye bir parola yoktur. sadece kırması uzun süre parola vardır.

/* if life="" then call BatsinBuDunya() */

üye olunpillinetwork sitelerine yorum ekleyebilmek ve daha fazlası için, üye olun ya da giriş yapın.

Bu yazıyı rapor et. Kural dışı içeriğe rastladığınızda editörlerimize rapor ederek müdahale edilmesini sağlayabilirsiniz. (Hangi durumlarda rapor edebilirim?)

Bu site

Nokta ve pilli ortak yapımı olan kodaman.org hep birlikte içerik üretip gelirini yazarları ile paylaştığımız kolektif bir kod yazarları blogudur. Siz de katılabilirsiniz.

pilliilan

son yorumlar

arama

pillinetwork