PDA

View Full Version : سوال: آیا با سی شارپ ساختار باینری یک فایل را می توان دید؟!



بیتا حکمت
یک شنبه 27 اردیبهشت 1394, 00:11 صبح
سلام . اگر درک اشتباهی از ساختار فایلها نداشته باشم ، اینطور می دونم که تمام فایلها به صورت باینری داخل حافظه ذخیره شدند .
حالا من یک سوال دارم آیا این امکان هست برنامه ای بنویسم که اون فایل رو صرف نظر از پسوندش باز کنم و ساختار باینری اش رو
ببینم ؟! به عبارت ساده تر و گویاتر :
آیا با سی شارپ می شود ، ساختار باینری یک فایل را دید ؟!

atpf67
یک شنبه 27 اردیبهشت 1394, 02:54 صبح
سلام بزرگوار

اینجا رو ببینید:
How to read file binary in C#? (http://stackoverflow.com/questions/2426190/how-to-read-file-binary-in-c)

shahryari
یک شنبه 27 اردیبهشت 1394, 07:27 صبح
متد ReadAllBytes در کلاس IO.File این کار رو براتون انجام میده

بیتا حکمت
یک شنبه 27 اردیبهشت 1394, 12:14 عصر
متد ReadAllBytes در کلاس IO.File این کار رو براتون انجام میده

سلام ، من نتونستم با این کد صفر و یک ها رو داخل تکست باکس بریزم




var x = File.ReadAllBytes(@"C:\Test\Timer.exe");
textBox1.Text = x.ToString();


یه سوال دیگه هم دارم ، ایا بعد اینکه اون ساختار باینری رو بدست آورد میشه همون رو به حالت اولش در آورد ، منظورم اینکه اول فایل ExE رو به باینری تبدیل کنم ، بعد
همون باینری رو دوباره به فایل Exe تبدیل کنم

Javad_raouf
یک شنبه 27 اردیبهشت 1394, 13:16 عصر
سلام
txt.Text = "";
byte[] allByte = System.IO.File.ReadAllBytes(@"C:\Rar.exe");
System.IO.File.WriteAllBytes(@"C:\Rar1.exe", allByte);
string strBinary = "";
for (int i = 0; i < allByte.Length; i++)
{
strBinary += Convert.ToString(allByte[i], 2);
}
txt.Text = strBinary;
برای یک فایل 300 کیلوبایتی 5 دقیقه طول کشید:افسرده:

SabaSabouhi
یک شنبه 27 اردیبهشت 1394, 13:21 عصر
سلام ، من نتونستم با این کد صفر و یک ها رو داخل تکست باکس بریزم




var x = File.ReadAllBytes(@"C:\Test\Timer.exe");
textBox1.Text = x.ToString();


یه سوال دیگه هم دارم ، ایا بعد اینکه اون ساختار باینری رو بدست آورد میشه همون رو به حالت اولش در آورد ، منظورم اینکه اول فایل ExE رو به باینری تبدیل کنم ، بعد
همون باینری رو دوباره به فایل Exe تبدیل کنم

سلام
خواهشمندم هدف خودت رو از این کار به ما بگی. شاید به‌تر بتونیم نظر بدیم.
طبیعی هست که شما نمی‌تونی یه آرایه از بایت رو توی textBox نمایش بدی.
کاری که می‌تونی بکنی اینه که مثل برنامه‌های دیگه‌ ( مثلاً HexEdit ) بیای
مقادیر رو به صورت Hex با یک فاصله نمایش بدی. مثلاً: FC 0A 00 00 00 BA
طبیعی هست که اگه اون x رو بدون تغییر توی یک فایل دیگه ذخیره کنی،
تبدیل به همون exe اولیه می‌شه.
اگه هم بخوای تغییر بدی، اگه ندونی داری چیکار می‌کنی، اون exe دیگه درست
کار نخواهد کرد.

صبا صبوحی

Javad_raouf
یک شنبه 27 اردیبهشت 1394, 13:38 عصر
این کد خیلی سریع تره به شرطی که خصوصیت WordWarp تکست باکست False باشه:
byte[] allByte = System.IO.File.ReadAllBytes(@"C:\Rar.exe");
StringBuilder sb = new StringBuilder();
for (int i = 0; i < allByte.Length; i++)
sb.Append(Convert.ToString(allByte[i], 2).PadLeft(8, '0'));
txt.Text = sb.ToString();
فایل 300 کیلوبایتی رو در عرض یک ثانیه آورد
بعد از اینکه 0 و 1 ها رو تغییر دادی برای ذخیره فایل جدید از این کد استفاده کن:
string strAllByte = txt.Text;
byte[] allByteNew = new byte[strAllByte.Length / 8];
for (int i = 0; i < strAllByte.Length; i+=8)
{
string t = strAllByte.Substring(i, 8);
allByteNew[i / 8] = Convert.ToByte(t, 2);
}
System.IO.File.WriteAllBytes(@"C:\Rar1.exe", allByteNew);

hoseinharami
یک شنبه 27 اردیبهشت 1394, 13:40 عصر
سلام
اگر بخوای این شکل باینری رو به همون شکل فایل دربیاری ، باید بدونی که کدوم باینری برای کدوم بایت بوده
وگرنه باینری ها غاطی میشن و نمی تونی از هم جداشون کنی
در نتیجه باید بریزیشون توی یک آرایه

بیتا حکمت
یک شنبه 27 اردیبهشت 1394, 13:44 عصر
سلام
خواهشمندم هدف خودت رو از این کار به ما بگی. شاید به‌تر بتونیم نظر بدیم.
طبیعی هست که شما نمی‌تونی یه آرایه از بایت رو توی textBox نمایش بدی.
کاری که می‌تونی بکنی اینه که مثل برنامه‌های دیگه‌ ( مثلاً HexEdit ) بیای
مقادیر رو به صورت Hex با یک فاصله نمایش بدی. مثلاً: FC 0A 00 00 00 BA
طبیعی هست که اگه اون x رو بدون تغییر توی یک فایل دیگه ذخیره کنی،
تبدیل به همون exe اولیه می‌شه.
اگه هم بخوای تغییر بدی، اگه ندونی داری چیکار می‌کنی، اون exe دیگه درست
کار نخواهد کرد.

صبا صبوحی

بس که برنامه هایی نوشتم که Insert و update بودن افسرده شدم :بامزه:
هر چند تو همون موارد هم خیلی چیزاست که یاد نگرفتم ، ولی به عنوان
زنگ تفریح میخوام به مواردی مثل فشرده کردن فایل و .. فکر کنم !( صرفا" برای تفریح ، نه هدف )
من از کسی پرسیدم اگر بتونم راهی پیدا کنم که فرضا" یک عدد 32 بیتی رو در 8 بیت ذخیره کنم ، ایا میشه
یه فشرده ساز درست کرد ؟ اونم گفت این کار شدنی نیست، اما اگر بتونی راهی براش پیدا کنی میشه ساخت !
تاکید می کنم که چیزی نیست که صب تا شب بشینم روی این موضوع وقت بزارم ، فقط مشتاقم فایل رو به باینری
تبدیل کنم و همون فایل رو برگردونم به EXE ، این وسط برای کنجکاوی بیت ها رو هم تغییر می دم

در واقع میخوام اعداد بزرگتر که به بیت های بیشتری نیاز دارند ، در بیت های کوچکتری ذخیره کنم .

Javad_raouf
یک شنبه 27 اردیبهشت 1394, 13:48 عصر
سلام
اگر بخوای این شکل باینری رو به همون شکل فایل دربیاری ، باید بدونی که کدوم باینری برای کدوم بایت بوده
وگرنه باینری ها غاطی میشن و نمی تونی از هم جداشون کنی
در نتیجه باید بریزیشون توی یک آرایه
منظورتون کد منه؟
کد من مشخصه دیگه هر 8 کاراکتر یک عدد باینری هستش
باید هنگام ویرایش دقت کنید
در هر صورت من کدم رو ویرایش کردم تا هر عدد باینری در یک خط نشون داده بشه و ویرایشش راحت تر باشه:
byte[] allByte = System.IO.File.ReadAllBytes(@"C:\Rar.exe");
StringBuilder sb = new StringBuilder();
for (int i = 0; i < allByte.Length; i++)
{
sb.Append(Convert.ToString(allByte[i], 2).PadLeft(8, '0') + Environment.NewLine);
}
txt.Text = sb.ToString();




string strAllByte = txt.Text.Replace(Environment.NewLine, "");
byte[] allByteNew = new byte[strAllByte.Length / 8];
for (int i = 0; i < strAllByte.Length; i+=8)
{
string t = strAllByte.Substring(i, 8);
allByteNew[i / 8] = Convert.ToByte(t, 2);
}
System.IO.File.WriteAllBytes(@"C:\Rar1.exe", allByteNew);

بیتا حکمت
یک شنبه 27 اردیبهشت 1394, 14:16 عصر
منظورتون کد منه؟
کد من مشخصه دیگه هر 8 کاراکتر یک عدد باینری هستش
باید هنگام ویرایش دقت کنید
در هر صورت من کدم رو ویرایش کردم تا هر عدد باینری در یک خط نشون داده بشه و ویرایشش راحت تر باشه:
byte[] allByte = System.IO.File.ReadAllBytes(@"C:\Rar.exe");
StringBuilder sb = new StringBuilder();
for (int i = 0; i < allByte.Length; i++)
{
sb.Append(Convert.ToString(allByte[i], 2).PadLeft(8, '0') + Environment.NewLine);
}
txt.Text = sb.ToString();




string strAllByte = txt.Text.Replace(Environment.NewLine, "");
byte[] allByteNew = new byte[strAllByte.Length / 8];
for (int i = 0; i < strAllByte.Length; i+=8)
{
string t = strAllByte.Substring(i, 8);
allByteNew[i / 8] = Convert.ToByte(t, 2);
}
System.IO.File.WriteAllBytes(@"C:\Rar1.exe", allByteNew);

یعنی همین باینری های بدست اومده از کد بالاتون رو با کد پایینی میشه به فایل ExE تبدیل کرد ؟!



string strAllByte = txt.Text;
byte[] allByteNew = new byte[strAllByte.Length / 8];
for (int i = 0; i < strAllByte.Length; i+=8)
{
string t = strAllByte.Substring(i, 8);
allByteNew[i / 8] = Convert.ToByte(t, 2);
}
System.IO.File.WriteAllBytes(@"C:\Rar1.exe", allByteNew);

Javad_raouf
یک شنبه 27 اردیبهشت 1394, 14:33 عصر
بله من امتحان کردم و فایل Exe هم دوباره قابل استفاده بود

SabaSabouhi
یک شنبه 27 اردیبهشت 1394, 15:49 عصر
بس که برنامه هایی نوشتم که Insert و update بودن افسرده شدم :بامزه:
هر چند تو همون موارد هم خیلی چیزاست که یاد نگرفتم ، ولی به عنوان
زنگ تفریح میخوام به مواردی مثل فشرده کردن فایل و .. فکر کنم !( صرفا" برای تفریح ، نه هدف )
من از کسی پرسیدم اگر بتونم راهی پیدا کنم که فرضا" یک عدد 32 بیتی رو در 8 بیت ذخیره کنم ، ایا میشه
یه فشرده ساز درست کرد ؟ اونم گفت این کار شدنی نیست، اما اگر بتونی راهی براش پیدا کنی میشه ساخت !
تاکید می کنم که چیزی نیست که صب تا شب بشینم روی این موضوع وقت بزارم ، فقط مشتاقم فایل رو به باینری
تبدیل کنم و همون فایل رو برگردونم به EXE ، این وسط برای کنجکاوی بیت ها رو هم تغییر می دم

در واقع میخوام اعداد بزرگتر که به بیت های بیشتری نیاز دارند ، در بیت های کوچکتری ذخیره کنم .


سلام
دوست عزیز، من حالا متوجه منظور شما شدم. اطلاعات مختصری دارم که در خدمت شما می‌گذارم.

1. اگه فایل رو بخونی، تغییرات بدی، ذخیره کنی. اگه بتونی در مرحله بعد، تغییرات رو به حالت اولیه برگردونی
هیچ مشکلی وجود نداره. برنامه‌های فشرده ساز موجود همین کار رو می‌کنن.

2. فشرده سازی، دقیقاً الگوریتم‌های ریاضی داره. و بر دو گونه هست. گونه‌ی اول حالتی هست که برای
فایل‌های Jpeg, Mp3, Mpeg و مشابه این‌ها استفاده می‌شه. در این نوع فشرده‌سازی گونه‌های بسیار کم
استفاده به گونه‌های نزدیک اما پر استفاده تبدیل می‌شن. ( مثلاً رنگ 0xFF3AB07F که فقط 6 بار در تصویر وجود
داره به رنگ 0xFF3BB077 ممکنه تبدیل بشه ) این تغییرات در تصویر ( Jpeg ) یا موزیک ( Mp3 ) یا فیلم ( Mpeg )
توسط حواس انسان قابل تشخیص نیست. اما این نوع فشرده‌سازی‌ها قابل برگشتن نیستن ( Lossy compression )
ولی حالت دوم که مورد نظر شما هست، با ایجاد جدول‌هایی توالی‌های تکرار شوند رو لیست می‌کنن و بجاش
از یک عبارت جایگزین استفاده می‌کنن.

3. اگه دوست داشته باشی، پیش‌نهاد می‌کنم کتابخونه‌ی SharpZipLib رو که رایگان هم هست دریافت کنی. به چند
متد فایل‌ها رو فشرده می‌کنه و بر می‌گردونه. و source هم کامله. هیچ چیز مخفی هم توش نداره.
چه بخواهی تو برنامه‌های ازش استفاده کنی و چه بخوای از روش کارش سر در بیاری بسیار چیز خوبی هست.

صبا صبوحی

RmeXXXXXXXXX
دوشنبه 28 اردیبهشت 1394, 19:09 عصر
اول برین سراغ الگوریتم های فشرده سازی (یک مثال ساده: درخت هافمن)
بعد رشته مطلب دستتون میاد
((( اول دانش کار بعد برنامه نویسی) )))

بیتا حکمت
دوشنبه 28 اردیبهشت 1394, 21:38 عصر
اول برین سراغ الگوریتم های فشرده سازی (یک مثال ساده: درخت هافمن)
بعد رشته مطلب دستتون میاد
((( اول دانش کار بعد برنامه نویسی) )))

والا من از اخر به اول راحت تر یاد می گیرم ،یعنی اول میخوام یه برنامه بنویسم بعد هی سوال پیش بیاد ، در این مسیر یاد می گیرم .

بیتا حکمت
جمعه 19 تیر 1394, 11:13 صبح
سلام مجدد دوستان ، دوستان کدی که اقای Javad_raouf (http://barnamenevis.org/member.php?124671-Javad_raouf) در پست شماره 7 نوشتن اجرا میشه و جواب می ده ، اما من سوادم قد نمی ده درک کنم که چرا وقتی اون صفر و یک ها رو داخل یک فایل تکست کپی می کنم حجم فابل به تقریبا 8.5 برابر میشه . چیزی که من میخوام اینکه ساختار یک فایل رو به باینری تبدیل کنم ( فقط صفر و یک ) ، اما وقتی همون صفر و یک ها درون فایل Txt کپی می کنم حجم فایل تکست با حجم فایل اصلی یکی باشه . ایا ایا از لحاظ منطقی چین چیزی غیر ممکنه ؟

arman_Delta2002
جمعه 19 تیر 1394, 11:37 صبح
بله غیر ممکنه
شما نمیتونین یک رشته 100 کاراکتری رو هم حجم بدوینن با یک رشته 1000 کاراکتری !
مگر این که به نحوی با الگریتم هایی این 1000 کاراکتر رو کوچیک کنین !
کمپرس کردن داده ها

Javad_raouf
دوشنبه 22 تیر 1394, 09:51 صبح
سلام مجدد دوستان ، دوستان کدی که اقای Javad_raouf (http://barnamenevis.org/member.php?124671-Javad_raouf)
در پست شماره 7 نوشتن اجرا میشه و جواب می ده ، اما من سوادم قد نمی ده درک کنم که چرا وقتی اون صفر و یک ها رو داخل یک فایل تکست کپی می کنم حجم فابل به تقریبا 8.5 برابر میشه . چیزی که من میخوام اینکه ساختار یک فایل رو به باینری تبدیل کنم ( فقط صفر و یک ) ، اما وقتی همون صفر و یک ها درون فایل Txt کپی می کنم حجم فایل تکست با حجم فایل اصلی یکی باشه . ایا ایا از لحاظ منطقی چین چیزی غیر ممکنه ؟
سلام
کاملا منطقیه که حجم فایلتون 8 برابر بشه
دقت کنید که توی بحث ذخیره سازی هر 8 بیت یک بایت محسوب میشه و هر بایت می تونه 2 به توان 8 حالت متفاوت داشته باشه مثلا 00000000 یک حالت هست و 00000001 یک حالت دیگه
حالا گاهی اوقات برای نمایش این حالت ها از کد اسکی استفاده می کنند که بین 0 تا 255 می تونه باشه و در حقیقت همون 2 به توان 8 هست ولی برای نمایش به جای 0 و 1 از 0 تا 9 استفاده می کنند و راحتتر نشون داده میشه
و گاهی اوقات به جای عدد از کاراکتر استفاده می کنند که هر کاراکتر به تنهایی می تونه نشان دهنده یکی از حالات بایت باشه مثلا کاراکتر a نشان دهنده کد اسکی 65 و کاراکتر # یک کد اسکی داره و ....
اینا همه پیش نیاز بود تا عرض کنم که وقی فایلی رو درون NotePad باز می کنید 0 و 1 هاش رو به شما نشون نمی ده بلکه کاراکترهای موجود در فایل رو نشون میده یعنی به ازای هر 8 بیت (یک بایت) یک کاراکتر نشون میده مثلا به جای 00110011 کاراکتر % رو نشون میده
وقتی شما اعداد 0 و 1 رو کپی می کنید توی NotePad در حقیقت شما دارید کاراکتر های 0و1 رو کپی می کنید که هر کدوم خودشون به تنهایی 8 بیت فضا می گیرن
---------------------------
برای اینکه بهتر متوجه بشید یک فایل متنی بسازید و توی اون حرف A رو تایپ کرده و Save کنید
حالا فایل رو با استفاده از کدی که من توی پست 7 نوشتم باز کنید
خواهید دید که کد 01000001 نشان داده خواهد شد این یعنی به جای تک کاراکتر A هشت رقم عدد نشون داده میشه
حالا همین 01000001 ها رو توی NotePad کپی کنید و Save کنید. بعدش فایل ذخیره شده رو دوباره توی نرم افزارتون باز کنید
این دفعه هشت تا عدد باینری 8 رقمی نشون داده میشه یعنی چی؟؟؟؟
این یعنی که NotePad که نمی فهمه شما دارید عدد باینری وارد می کنید اون هر کدام از صفر و یک ها رو یک کاراکتر درنظر می گیره و ذخیره می کنه
امیدوارم تونسته باشم انتقال بدم:افسرده:

بیتا حکمت
دوشنبه 22 تیر 1394, 11:33 صبح
خیلی ممنون از اینکه وقت گذاشتین و جواب دادین ، واقعیتش من تصور اشتباهی دادم و مواردی رو گفتین نمی دونستم ، من بازم میخوام از شما و بقیه دوستان بیشتر یاد بگیرم ، با این شیوه بهتر یاد می گیرم تا خوندن کتابهای دانشگاهی ( اما سوالاتم تو این تاپیک حیاتی نیست ، اگر وقت داشتین ممنون میشم بازم راهنمایی کنید )

_

تو این لینک ، کدی (https://msdn.microsoft.com/en-us/library/system.io.file.readallbytes%28v=vs.110%29.aspx)ه ت که فایل رو بایت به بایت میخونه



byte[] array = File.ReadAllBytes(@"C:\Users\bita\Desktop\Timer.exe");
array[array.Length - 1] MessageBox.Show(array.Length .ToString());




می دونید که خروجی array.Length یک عدد صحیح است ، از طرفی برای خوندن فایل بایت به بایت باید طول فایل رو بدست بیارم ، اگر طول فایلی خیلی بزرگ باشه ( از محدود Int بزرگتر )
، چطور می تونم بایت های فایل رو بدست بیارم ، چون حتما برای فایل های خیلی بزرگ array.Length خطا می ده

پ ن : هر زمان وقت داشتین جواب بدین ، این تاپیک برام فقط جنبه یادگیری و سرگرمی داره

golbafan
دوشنبه 22 تیر 1394, 17:57 عصر
والا من از اخر به اول راحت تر یاد می گیرم ،یعنی اول میخوام یه برنامه بنویسم بعد هی سوال پیش بیاد ، در این مسیر یاد می گیرم .

روش خوبیه (البته اعتماد به نفس بالایی میخواد)
راستش من اولین برنامه ای رو که برای مشتری نوشتم (فکر کنم حوالی سال 78 بود) در حالی استارت زدم که اصلا نمیدونستم برنامه نویسی چی هست!!!