業務用エアコン関連の技術情報、エラーコード、環境問題対策に関する別サイト「エアコンの安全な修理・適切なフロン回収」

Slackware15 : Suricata , Elasticsearch , Kibana Install

Prerequisites

1.Suricata
SURICATA IDS/IPS is an open source IDS that monitors communications on the network and detects suspicious traffic.
The basic mechanism is signature-based, so it can detect predefined unauthorized communications. Suricata is also characterized by its ability to provide protection as well as detection.

2.Elastic Stack,Kibana,Filebeat
Install and configure the Elastic Stack to enable visualization and search of SURICATA logs using Kibana and Filebeat.

This time, we will install Suricata IDS and ElasticStack on the following server.
・First Server Suricata IDS & Filebeat : Slackware15.0 IP address(192.168.11.83)
・Second server Elasticsearch & kibana  : Slackware15.0 IP address(192.168.11.85)

First Server: Suricata Installation

1.Installing Required Packages, Such as Rust

Since Slackware 15 comes with version 1.58 installed by default, I will install Rust 1.75.

# curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh

When you run it, a menu will appear asking for your installation options.1) Proceed with standard installation (default - just press enter))
2) Customize installation
3) Cancel installation
>Enter 1 (the default)

# source "$HOME/.cargo/env"
# rustup toolchain install 1.75
# rustup default 1.75

Check Version
# rustc --version
rustc 1.75.0 (82e1608df 2023-12-21)
# cargo --version
cargo 1.75.0 (1d8b05cdd 2023-11-20)
# slackpkg install libnfnetlink
# slackpkg install libnetfilter_queue 

2.Installing and Configuring Suricata

2.1 Download

# wget https://www.openinfosecfoundation.org/download/suricata-8.0.6.tar.gz
# tar -xvzf suricata-8.0.6.tar.gz
# cd suricata-8.0.6

2.2 Install

Run `configure` with the necessary options
# ./configure --prefix=/usr --sysconfdir=/etc --localstatedir=/var   --enable-nfqueue

Compile
# make

Run the installation
# make install-full

Check Version
# suricata -V
This is Suricata version 8.0.6 RELEASE

2.3 Determine interface and IP address where Suricata will inspect network packets

# ip --brief add
lo               UNKNOWN        127.0.0.1/8 ::1/128
eth0             UP             192.168.11.83/24 fe80::20c:29ff:fe31:b405/64

2.4 Edit configuration file

# vi /etc/suricata/suricata.yaml
 
Line 18: Comment it out and add below (in the vars section, define the network)
#HOME_NET: "[192.168.0.0/16,10.0.0.0/8,172.16.0.0/12]"
HOME_NET: "[192.168.11.0/24]"
 
Around line 158: Change
community-id: false → community-id: true
 
Around line 661: Set the interface name in the af-packet section
af-packet:
    - interface: eth0

2.5 Updating Suricata Rules

# suricata-update

2.6 Activate Suricata

Creating a Startup Script

# vi /etc/rc.d/rc.suricata

#!/bin/sh
#
# /etc/rc.d/rc.suricata
#
# Suricata Start/Stop Scripts for Slackware 15.0
#

# Network Interface to Use
INTERFACE="eth0"

# Configuring Various Paths (Please adjust according to your environment)
SURICATA_BIN="/usr/bin/suricata"
SURICATA_CONF="/etc/suricata/suricata.yaml"
PID_FILE="/var/run/suricata.pid"

# Option Settings
OPTIONS="-D -c $SURICATA_CONF --af-packet=$INTERFACE --pidfile $PID_FILE"

suricata_start() {
  if [ -s $PID_FILE ]; then
    if ps -p $(cat $PID_FILE) > /dev/null 2>&1; then
      echo "Suricata is already running."
      return
    fi
  fi
  
  if [ -x $SURICATA_BIN ]; then
    echo "Starting Suricata ($INTERFACE)..."
    $SURICATA_BIN $OPTIONS
  else
    echo "Error: $SURICATA_BIN cannot be found, or you do not have permission to run it."
  fi
}

suricata_stop() {
  if [ -s $PID_FILE ]; then
    PID=$(cat $PID_FILE)
    echo "Stopping Suricata (PID: $PID)..."
    kill $PID
    #Wait a moment until it comes to a complete stop
    while ps -p $PID > /dev/null 2>&1; do sleep 1; done
    rm -f $PID_FILE
  else
    echo "Suricata is not running (the PID file cannot be found)."
  fi
}

suricata_restart() {
  suricata_stop
  sleep 1
  suricata_start
}

suricata_status() {
  if [ -s $PID_FILE ]; then
    PID=$(cat $PID_FILE)
    if ps -p $PID > /dev/null 2>&1; then
      echo "Suricata is running (PID: $PID)。"
    else
      echo "Suricata has stopped, but the old PID file remains."
    fi
  else
    echo "Suricata is stopped."
  fi
}

case "$1" in
  'start')
    suricata_start
    ;;
  'stop')
    suricata_stop
    ;;
  'restart')
    suricata_restart
    ;;
  'status')
    suricata_status
    ;;
  *)
    echo "How to Use: $0 {start|stop|restart|status}"
    exit 1
esac

# chmod +x /etc/rc.d/rc.suricata
# /etc/rc.d/rc.suricata start

Check the stats.log file for statistics (updated every 8 seconds by default)

# tail -f /var/log/suricata/stats.log

A more advanced output, EVE JSON, can be generated with the following command

# tail -f /var/log/suricata/eve.json

2.7 Add a Ruleset
Suricata includes a tool called suricata-update that allows you to retrieve rule sets from external providers. Running the command below will download the latest rule set for the Suricata server:

# suricata-update -o /var/lib/suricata/rules

-------------------------------------------------------------
17/9/2026 -- 12:19:44 - <Info> -- Ignoring file f625293e2432dbf07497d06349de6f0b/rules/emerging-deleted.rules
17/9/2026 -- 12:19:45 - <Info> -- Loaded 68724 rules.
17/9/2026 -- 12:19:46 - <Info> -- Disabled 15 rules.
17/9/2026 -- 12:19:46 - <Info> -- Enabled 0 rules.
17/9/2026 -- 12:19:46 - <Info> -- Modified 0 rules.
17/9/2026 -- 12:19:46 - <Info> -- Dropped 0 rules.
17/9/2026 -- 12:19:46 - <Info> -- Enabled 136 rules for flowbit dependencies.
17/9/2026 -- 12:19:46 - <Info> -- Backing up current rules.
17/9/2026 -- 12:19:46 - <Info> -- Writing rules to /var/lib/suricata/rules/suricata.rules: total: 68724; enabled: 52770; added: 68724; removed 0; modified: 0
17/9/2026 -- 12:19:46 - <Info> -- Writing /var/lib/suricata/rules/classification.config
17/9/2026 -- 12:19:46 - <Info> -- Testing with suricata -T.
17/9/2026 -- 12:20:15 - <Info> -- Done.

This indicates that suricata-update retrieved the free Emerging Threats ET Open Rules and saved them to the /etc/suricata/rules/suricata.rules file in Suricata. It also shows the number of rules processed; in this example, 68,724 were added, of which 52,770 were enabled.

2.8 Add a rule set provider.
Index list of sources providing rule sets

# suricata-update list-sources

Name: abuse.ch/feodotracker
  Vendor: Abuse.ch
  Summary: Abuse.ch Feodo Tracker Botnet C2 IP ruleset
  License: CC0-1.0
Name: abuse.ch/sslbl-blacklist
  Vendor: Abuse.ch
  Summary: Abuse.ch SSL Blacklist
  License: CC0-1.0
  Replaces: sslbl/ssl-fp-blacklist
Name: abuse.ch/sslbl-c2
  Vendor: Abuse.ch
  Summary: Abuse.ch Suricata Botnet C2 IP Ruleset
  License: CC0-1.0
Name: abuse.ch/sslbl-ja3
  Vendor: Abuse.ch
  Summary: Abuse.ch Suricata JA3 Fingerprint Ruleset
  License: CC0-1.0
  Replaces: sslbl/ja3-fingerprints
Name: abuse.ch/urlhaus
  Vendor: abuse.ch
  Summary: Abuse.ch URLhaus Suricata Rules
  License: CC0-1.0
Name: aleksibovellan/nmap
  Vendor: aleksibovellan
  Summary: Suricata IDS/IPS Detection Rules Against NMAP Scans
  License: MIT
Name: et/open
  Vendor: Proofpoint
  Summary: Emerging Threats Open Ruleset
  License: MIT
Name: et/pro
  Vendor: Proofpoint
  Summary: Emerging Threats Pro Ruleset
  License: Commercial
  Replaces: et/open
  Parameters: secret-code
  Subscription: https://www.proofpoint.com/us/threat-insight/et-pro-ruleset
Name: etnetera/aggressive
  Vendor: Etnetera a.s.
  Summary: Etnetera aggressive IP blacklist
  License: MIT
Name: oisf/trafficid
  Vendor: OISF
  Summary: Suricata Traffic ID ruleset
  License: MIT
Name: pawpatrules
  Vendor: pawpatrules
  Summary: PAW Patrules is a collection of rules for IDPS / NSM Suricata engine
  License: CC-BY-SA-4.0
Name: ptrules/open
  Vendor: Positive Technologies
  Summary: Positive Technologies Open Ruleset
  License: Custom
Name: scwx/enhanced
  Vendor: Secureworks
  Summary: Secureworks suricata-enhanced ruleset
  License: Commercial
  Parameters: secret-code
  Subscription: https://www.secureworks.com/contact/ (Please reference CTU Countermeasures)
Name: scwx/malware
  Vendor: Secureworks
  Summary: Secureworks suricata-malware ruleset
  License: Commercial
  Parameters: secret-code
  Subscription: https://www.secureworks.com/contact/ (Please reference CTU Countermeasures)
Name: scwx/security
  Vendor: Secureworks
  Summary: Secureworks suricata-security ruleset
  License: Commercial
  Parameters: secret-code
  Subscription: https://www.secureworks.com/contact/ (Please reference CTU Countermeasures)
Name: stamus/lateral
  Vendor: Stamus Networks
  Summary: Lateral movement rules
  License: GPL-3.0-only
Name: stamus/nrd-14-open
  Vendor: Stamus Networks
  Summary: Newly Registered Domains Open only - 14 day list, complete
  License: Commercial
  Parameters: secret-code
  Subscription: https://www.stamus-networks.com/stamus-labs/subscribe-to-threat-intel-feed
Name: stamus/nrd-30-open
  Vendor: Stamus Networks
  Summary: Newly Registered Domains Open only - 30 day list, complete
  License: Commercial
  Parameters: secret-code
  Subscription: https://www.stamus-networks.com/stamus-labs/subscribe-to-threat-intel-feed
Name: stamus/nrd-entropy-14-open
  Vendor: Stamus Networks
  Summary: Newly Registered Domains Open only - 14 day list, high entropy
  License: Commercial
  Parameters: secret-code
  Subscription: https://www.stamus-networks.com/stamus-labs/subscribe-to-threat-intel-feed
Name: stamus/nrd-entropy-30-open
  Vendor: Stamus Networks
  Summary: Newly Registered Domains Open only - 30 day list, high entropy
  License: Commercial
  Parameters: secret-code
  Subscription: https://www.stamus-networks.com/stamus-labs/subscribe-to-threat-intel-feed
Name: stamus/nrd-phishing-14-open
  Vendor: Stamus Networks
  Summary: Newly Registered Domains Open only - 14 day list, phishing
  License: Commercial
  Parameters: secret-code
  Subscription: https://www.stamus-networks.com/stamus-labs/subscribe-to-threat-intel-feed
Name: stamus/nrd-phishing-30-open
  Vendor: Stamus Networks
  Summary: Newly Registered Domains Open only - 30 day list, phishing
  License: Commercial
  Parameters: secret-code
  Subscription: https://www.stamus-networks.com/stamus-labs/subscribe-to-threat-intel-feed
Name: tgreen/hunting
  Vendor: tgreen
  Summary: Threat hunting rules
  License: GPLv3

Enable source (if tgreen/hunting is enabled)

# suricata-update enable-source tgreen/hunting

19/9/2026 -- 09:43:26 - <Info> -- Using data-directory /var/lib/suricata.
19/9/2026 -- 09:43:26 - <Info> -- Using Suricata configuration /etc/suricata/suricata.yaml
19/9/2026 -- 09:43:26 - <Info> -- Using /usr/share/suricata/rules for Suricata provided rules.
19/9/2026 -- 09:43:26 - <Info> -- Found Suricata version 8.0.6 at /usr/bin/suricata.
19/9/2026 -- 09:43:26 - <Warning> -- Source index does not exist, will use bundled one.
19/9/2026 -- 09:43:26 - <Warning> -- Please run suricata-update update-sources.
19/9/2026 -- 09:43:26 - <Info> -- Creating directory /var/lib/suricata/update/sources
19/9/2026 -- 09:43:26 - <Info> -- Enabling default source et/open
19/9/2026 -- 09:43:26 - <Info> -- Source tgreen/hunting enabled

Perform update

# suricata-update update-sources

3.Testing the Suricata Configuration

3.1 Testing the Configuration File

# suricata -T -c /etc/suricata/suricata.yaml -v

Notice: suricata: This is Suricata version 8.0.6 RELEASE running in SYSTEM mode
Info: cpu: CPUs/cores online: 2
Info: suricata: Running suricata under test mode
Info: suricata: Setting engine mode to IDS mode by default
Info: exception-policy: master exception-policy set to: auto
Info: suricata: Preparing unexpected signal handling
Info: logopenfile: fast output device (regular) initialized: fast.log
Info: logopenfile: eve-log output device (regular) initialized: eve.json
Info: logopenfile: stats output device (regular) initialized: stats.log
Info: detect: 1 rule files processed. 52823 rules successfully loaded, 0 rules failed, 0 rules skipped
Info: threshold-config: Threshold config parsed: 0 rule(s) found
Info: detect: 52828 signatures processed. 1229 are IP-only rules, 4534 are inspecting packet payload, 46829 inspect application layer, 110 are decoder event only
Notice: suricata: Configuration provided was successfully loaded. Exiting.

Restart the Suricata service

# /etc/rc.d/rc.suricata restart

Check the log file

# tail -f /var/log/suricata/suricata.log

[16572 - Suricata-Main] 2026-09-19 09:45:25 Info: logopenfile: fast output device (regular) initialized: fast.log
[16572 - Suricata-Main] 2026-09-19 09:45:25 Info: logopenfile: eve-log output device (regular) initialized: eve.json
[16572 - Suricata-Main] 2026-09-19 09:45:25 Info: logopenfile: stats output device (regular) initialized: stats.log
[16572 - Suricata-Main] 2026-09-19 09:45:27 Info: detect: 1 rule files processed. 52823 rules successfully loaded, 0 rules failed, 0 rules skipped
[16572 - Suricata-Main] 2026-09-19 09:45:27 Info: threshold-config: Threshold config parsed: 0 rule(s) found
[16572 - Suricata-Main] 2026-09-19 09:45:27 Info: detect: 52828 signatures processed. 1229 are IP-only rules, 4534 are inspecting packet payload, 46829 inspect application layer, 110 are decoder event only
[16572 - Suricata-Main] 2026-09-19 09:45:31 Info: unix-manager: unix socket '/var/run/suricata/suricata-command.socket'
[16572 - Suricata-Main] 2026-09-19 09:45:31 Info: runmodes: eth0: creating 2 threads
[16574 - W#01-eth0] 2026-09-19 09:45:31 Info: ioctl: eth0: MTU 1500
[16572 - Suricata-Main] 2026-09-19 09:45:32 Notice: threads: Threads created -> W: 2 FM: 1 FR: 1   Engine started.

4.Creating and Testing Suricata Custom Rules

4.1 Create a file containing customer rules

# vi /var/lib/suricata/rules/local.rules
Please include the following information
alert icmp any any -> any any (msg:"ICMP Ping"; sid:100001; rev:1;)

4.2 Edit the configuration file (define the path for a new rule)

# vi /etc/suricata/suricata.yaml
 
# Add the following around line 2333
default-rule-path: /var/lib/suricata/rules
 
rule-files:
  - suricata.rules
  - local.rules

4.3 Testing the Configuration File

# suricata -T -c /etc/suricata/suricata.yaml -v

Notice: suricata: This is Suricata version 8.0.6 RELEASE running in SYSTEM mode
Info: cpu: CPUs/cores online: 2
Info: suricata: Running suricata under test mode
Info: suricata: Setting engine mode to IDS mode by default
Info: exception-policy: master exception-policy set to: auto
Info: suricata: Preparing unexpected signal handling
Info: logopenfile: fast output device (regular) initialized: fast.log
Info: logopenfile: eve-log output device (regular) initialized: eve.json
Info: logopenfile: stats output device (regular) initialized: stats.log
Info: detect: 2 rule files processed. 52824 rules successfully loaded, 0 rules failed, 0 rules skipped
Info: threshold-config: Threshold config parsed: 0 rule(s) found
Info: detect: 52829 signatures processed. 1230 are IP-only rules, 4534 are inspecting packet payload, 46829 inspect application layer, 110 are decoder event only
Notice: suricata: Configuration provided was successfully loaded. Exiting.

Restarting the Suricat service

# /etc/rc.d/rc.suricata restart

4.4 Testing the Application of Custom Rules
Run a ping on another device on the same local network to see if it was logged.

# cat /var/log/suricata/fast.log
09/19/2026-09:48:54.822402  [**] [1:100000:1] ICMP Ping [**] [Classification: (null)] [Priority: 3] {ICMP} 192.168.11.14:8 -> 192.168.11.83:0
09/19/2026-09:48:54.822426  [**] [1:100000:1] ICMP Ping [**] [Classification: (null)] [Priority: 3] {ICMP} 192.168.11.83:0 -> 192.168.11.14:0

To retrieve logs in JSON format, install jq on the system.

# wget -O /usr/local/bin/jq https://github.com/jqlang/jq/releases/download/jq-1.8.2/jq-linux-amd64
# chmod +x /usr/local/bin/jq
# jq --version
jq-1.8.2

Run the following command to ping another device on the same local network

# tail -f /var/log/suricata/eve.json | jq 'select(.event_type=="alert")'
When you run "ping," the following is displayed on the console:
{
  "timestamp": "2026-09-19T10:19:57.095039+0900",
  "flow_id": 1533994348757840,
  "in_iface": "eth0",
  "event_type": "alert",
  "src_ip": "192.168.11.83",
  "dest_ip": "192.168.11.14",
  "proto": "ICMP",
  "ip_v": 4,
  "icmp_type": 0,
  "icmp_code": 0,
  "pkt_src": "wire/pcap",
  "community_id": "1:K09ijpWpwrp7sSrxOGACqhHkilo=",
  "alert": {
    "action": "allowed",
    "gid": 1,
    "signature_id": 100001,
    "rev": 1,
    "signature": "ICMP Ping",
    "category": "",
    "severity": 3
  },

5.Configuring Suricata as an IPS

By default, SURICATA operates in IDS mode and does not actively block network traffic. To switch to IPS mode, you must change SURICATA's default settings.

5.1 Enabling nfqueue Mode

# vi /etc/rc.d/rc.suricata
Make the following changes:
#OPTIONS="-D -c $SURICATA_CONF --af-packet=$INTERFACE --pidfile $PID_FILE"
OPTIONS="-D -q 0 -c $SURICATA_CONF --pidfile $PID_FILE"

Reload the settings and restart Suricata

# /etc/rc.d/rc.suricata restart

5.2 UFW Settings for Sending Traffic to Suricata

# vi /etc/ufw/before.rules

Add the following to line 19
# Don't delete these required lines, otherwise there will be errors
*filter
:ufw-before-input - [0:0]
:ufw-before-output - [0:0]
:ufw-before-forward - [0:0]
:ufw-not-local - [0:0]
# End required lines

## Start Suricata NFQUEUE rules
-I INPUT 1 -p tcp --dport 22 -j NFQUEUE --queue-bypass
-I OUTPUT 1 -p tcp --sport 22 -j NFQUEUE --queue-bypass
-I FORWARD -j NFQUEUE
-I INPUT 2 -j NFQUEUE
-I OUTPUT 2 -j NFQUEUE
## End Suricata NFQUEUE rules

For IPv6, edit the following file in the same way

# vi /etc/ufw/before6.rules

Restart the UFW service

# /etc/rc.d/rc.ufw restart

Elasticsearch

I'll be working on my second Slackware 15.0 machine (IP: 192.168.11.85).

1. OpenJDK Install

Since Elasticsearch requires OpenJDK, let's install it.
Please refer to the page below for installation instructions.

2. Creating Dedicated Users and Groups

For security reasons, Elasticsearch cannot be started as the root user. Create a dedicated Elasticsearch user.

Creating a Group (Specify an available GID as appropriate)
# groupadd -g 252 elasticsearch

Creating a User
# useradd -u 252 -g elasticsearch -d /usr/share/elasticsearch -s /bin/false elasticsearch

3. Downloading and Unzipping the Archive

Download the official archive for Linux x86_64 and place it in a directory such as /usr/share.

# cd /tmp

# wget https://artifacts.elastic.co/downloads/elasticsearch/elasticsearch-8.19.12-linux-x86_64.tar.gz

Unfold and place
# tar -xzf elasticsearch-8.19.12-linux-x86_64.tar.gz
# mv elasticsearch-8.19.12 /usr/share/elasticsearch

Change ownership to the elasticsearch user
# chown -R elasticsearch:elasticsearch /usr/share/elasticsearch

4. Creating a Directory

If you want to manage the directories for logs, data, and configuration files separately, create them and assign permissions.

# mkdir -p /var/log/elasticsearch /var/lib/elasticsearch /etc/elasticsearch

Copy the default configuration file
# cp -R /usr/share/elasticsearch/config/* /etc/elasticsearch/
# chown -R elasticsearch:elasticsearch /var/log/elasticsearch /var/lib/elasticsearch /etc/elasticsearch


5.Editing the Configuration File (elasticsearch.yml)

Edit /etc/elasticsearch/elasticsearch.yml to configure the basic settings.

# vi /etc/elasticsearch/elasticsearch.yml

Specifying a Path
path.data: /var/lib/elasticsearch
path.logs: /var/log/elasticsearch

Network Settings
network.host: 192.168.11.85
http.port: 9200

When running on a single node (such as in a test environment)
discovery.type: single-node

# 8.x and later: If you want to temporarily disable the security features (TLS/authentication) that are enabled by default for testing purposes (not recommended for production environments), follow the steps below:
xpack.security.enabled: false


6.Creating a Startup Script (Slackware Method)

Create the following directory in advance

# mkdir /var/run/elasticsearch
# chown -R elasticsearch:elasticsearch  /var/run/elasticsearch

Creating the /etc/rc.d/rc.elasticsearch script for Slackware

# vi /etc/rc.d/rc.elasticsearch

Please fill in the following
#!/bin/sh
#
# /etc/rc.d/rc.elasticsearch
#
# Slackware init script for Elasticsearch
#

# Various Passes and User Settings
ES_USER="elasticsearch"
ES_GROUP="elasticsearch"
ES_HOME="/usr/share/elasticsearch"
ES_BIN="$ES_HOME/bin/elasticsearch"
PID_FILE="/var/run/elasticsearch/elasticsearch.pid"

# Elasticsearch Startup Process
elasticsearch_start() {
  if [ -f "$PID_FILE" ]; then
    if ps -p $(cat "$PID_FILE") > /dev/null 2>&1; then
      echo "Elasticsearch is already running."
      return
    else
      echo "Removing stale PID file: $PID_FILE"
      rm -f "$PID_FILE"
    fi
  fi

  echo "Starting Elasticsearch..."
  
  # Checking Permissions for the PID Storage Directory
  PID_DIR=$(dirname "$PID_FILE")
  if [ ! -d "$PID_DIR" ]; then
    mkdir -p "$PID_DIR"
    chown "$ES_USER":"$ES_GROUP" "$PID_DIR"
  fi

  #To prevent execution as root, run in the background (-d) using a dedicated user
  # Use the -p option to write a PID file
  su -s /bin/bash -c "$ES_BIN -d -p $PID_FILE" $ES_USER
}

# Shutting Down Elasticsearch
elasticsearch_stop() {
  if [ -f "$PID_FILE" ]; then
    PID=$(cat "$PID_FILE")
    echo "Stopping Elasticsearch (PID $PID)..."
    kill $PID
    
    # Wait a moment until it comes to a complete stop
    TIMEOUT=30
    while ps -p $PID > /dev/null 2>&1; do
      sleep 1
      TIMEOUT=$((TIMEOUT - 1))
      if [ $TIMEOUT -le 0 ]; then
        echo "Elasticsearch did not stop gracefully. Forcing..."
        kill -9 $PID
        break
      fi
    done
    rm -f "$PID_FILE"
  else
    echo "Elasticsearch is not running (no PID file found)."
  fi
}

# Check Status
elasticsearch_status() {
  if [ -f "$PID_FILE" ]; then
    PID=$(cat "$PID_FILE")
    if ps -p $PID > /dev/null 2>&1; then
      echo "Elasticsearch is running with PID $PID."
    else
      echo "Elasticsearch is NOT running, but PID file exists."
    fi
  else
    echo "Elasticsearch is stopped."
  fi
}

# Branching Based on Arguments
case "$1" in
  'start')
    elasticsearch_start
    ;;
  'stop')
    elasticsearch_stop
    ;;
  'restart')
    elasticsearch_stop
    sleep 2
    elasticsearch_start
    ;;
  'status')
    elasticsearch_status
    ;;
  *)
    echo "Usage: $0 {start|stop|restart|status}"
    exit 1
esac

exit 0

Granting Execution Permissions

# chmod +x /etc/rc.d/rc.elasticsearch

Startup and Functionality Check

Startup
# /etc/rc.d/rc.elasticsearch start

Stop
# /etc/rc.d/rc.elasticsearch stop

Restart
/e# tc/rc.d/rc.elasticsearch restart

Status Check
# /etc/rc.d/rc.elasticsearch status

7. Autostart Settings

If you want this to start automatically when the OS boots, add the following to /etc/rc.d/rc.local.

# vi /etc/rc.d/rc.local 
Please fill in the information below
if [ -x /etc/rc.d/rc.elasticsearch ]; then
  /etc/rc.d/rc.elasticsearch start
fi

8.  Create passwords for elastic and kibana_system
Be sure to copy the passwords for the elastic user and kibana_system user, as they will be needed later.
The kibana_system user is used for configuring Kibana.
The elastic user is used for configuring Filebeat and Auditbeat, and for logging into Kibana.
If you forget your password, you can use the command again to reset it.

[elastic] User password creation

# cd /usr/share/elasticsearch/bin
 
# ./elasticsearch-reset-password -u elastic
This tool will reset the password of the [elastic] user to an autogenerated value.
The password will be printed in the console.
Please confirm that you would like to continue [y/N]y
 
 
Password for the [elastic] user successfully reset.
New value: l3=c2+QzGDJUzsxi0*47

※Resetting Elasticsearch Passwords
The automatically generated Elastic user password is too complex, so you can reset it using the /usr/share/elasticsearch/bin/elasticsearch-reset-password command.
To reset your password, execute the command.

# /usr/share/elasticsearch/bin/elasticsearch-reset-password -u elastic -i
 
This tool will reset the password of the [elastic] user.
You will be prompted to enter the password.
Please confirm that you would like to continue [y/N]y
 
 
Enter password for [elastic]:
Re-enter password for [elastic]: 
Password for the [elastic] user successfully reset.

[kibana_system] User Password Creation

# cd /usr/share/elasticsearch/bin
 
# ./elasticsearch-reset-password -u kibana_system
This tool will reset the password of the [kibana_system] user to an autogenerated value.
The password will be printed in the console.
Please confirm that you would like to continue [y/N]y
 
 
Password for the [kibana_system] user successfully reset.
New value: bctctD9JbJL7tfe0_o4b

9. Connectivity Test

Use curl to verify that it is running properly. (Alternatively, accsess https://192.168.11.85:9200 in a web browser.)

# curl -k -u elastic https://192.168.11.85:9200
It is displayed as shown below
Enter host password for user 'elastic':
{
  "name" : "Lion.korodes.com",
  "cluster_name" : "elasticsearch",
  "cluster_uuid" : "ZMJ6oRhGT36FfdG177AltA",
  "version" : {
    "number" : "8.19.12",
    "build_flavor" : "default",
    "build_type" : "tar",
    "build_hash" : "840cd2a58b052d1632219ee0b8dcc0f364226287",
    "build_date" : "2026-02-23T23:08:40.713020893Z",
    "build_snapshot" : false,
    "lucene_version" : "9.12.2",
    "minimum_wire_compatibility_version" : "7.17.0",
    "minimum_index_compatibility_version" : "7.0.0"
  },
  "tagline" : "You Know, for Search"
}

Kibana

I'll be working on my second Slackware 15.0 machine (IP: 192.168.11.85).

1. Kibana Install

# cd /usr/local
# wget https://artifacts.elastic.co/downloads/kibana/kibana-8.19.21-linux-x86_64.tar.gz
# tar -xzf kibana-8.19.21-linux-x86_64.tar.gz
# mv kibana-8.19.21 /usr/local/kibana

2. Creating a Kibana User

# useradd -r -s /bin/false kibana
# chown -R kibana:kibana /usr/local/kibana

3. Editing Kibana Configuration Files

# vi /usr/local/kibana/config/kibana.yml

server.port: 5601
server.host: "192.168.11.85"
elasticsearch.hosts: ["https://191.168.11.85:9200"]
elasticsearch.username: "kibana_system"
elasticsearch.password: "your_password"
elasticsearch.ssl.certificateAuthorities: [ "/usr/share/elasticsearch/config/certs/http_ca.crt" ]
# chmod a+rx /usr/share/elasticsearch/config/certs
# chmod a+r /usr/share/elasticsearch/config/certs/http_ca.crt

4. Launching Kibana

If you want to run a process manually in the background, such as for temporary testing

# su -s /bin/bash kibana -c "/usr/local/kibana/bin/kibana &"

Launch Kibana and configure it to run at system startup.

# vi /etc/rc.d/rc.kibana

#!/bin/bash
#
# /etc/rc.d/rc.kibana
# Start/stop/restart the Kibana service.

# Target directory
TARGET_DIR="/usr/local/kibana"

cd "$TARGET_DIR"

export PATH="/usr/local/kibana/node/glibc-217/bin:$PATH"

KIBANA_BIN=" /usr/local/kibana/bin/kibana"
KIBANA_USER="kibana"
PID_FILE="/var/run/kibana.pid"
LOG_FILE="/var/log/kibana.log"

kibana_start() {
  if [ -f $PID_FILE ]; then
    echo "Kibana is already running."
  else
    echo "Starting Kibana..."
    # Run in the background as a Kibana user
    nohup su -s /bin/sh $KIBANA_USER -c "$KIBANA_BIN >> $LOG_FILE 2>&1" &
    echo $! > $PID_FILE
    # Adjusting Log File Permissions
    touch $LOG_FILE && chown $KIBANA_USER:$KIBANA_USER $LOG_FILE
  fi
}

kibana_stop() {
  if [ -f $PID_FILE ]; then
    echo "Stopping Kibana..."
    kill $(cat $PID_FILE)
    rm -f $PID_FILE
  else
    echo "Kibana is not running."
  fi
}

kibana_restart() {
  kibana_stop
  sleep 2
  kibana_start
}

kibana_status() {
  if [ -f $PID_FILE ]; then
    echo "Kibana is running with PID $(cat $PID_FILE)."
  else
    echo "Kibana is stopped."
  fi
}

case "$1" in
  'start')
    kibana_start
    ;;
  'stop')
    kibana_stop
    ;;
  'restart')
    kibana_restart
    ;;
  'status')
    kibana_status
    ;;
  *)
    echo "usage $0 start|stop|restart"
esac
# chmod +x /etc/rc.d/rc.kibana
# /etc/rc.d/rc.kibana start

Filebeat 9 Install

To collect and monitor logs from the first server (Slackware 15.0) using the ELK Stack, you need to install Filebeat.
This procedure will be performed on the first server (Slackware 15.0) with the IP address 192.168.11.83.

1. Install

# cd /usr/local/src
# curl -L -O https://artifacts.elastic.co/downloads/beats/filebeat/filebeat-9.5.4-linux-x86_64.tar.gz
# cd /usr/local
# tar -xzvf /usr/local/src/filebeat-9.5.4-linux-x86_64.tar.gz

# Create symbolic links for easier management
# ln -s filebeat-9.5.4-linux-x86_64 filebeat

2. Filebeat Logging Configuration

The default Filebeat configuration file is /usr/local/filebeat/filebeat.yml.
To configure Filebeat to write logs to its own log file, enter the following settings in the configuration file:

# cat >> /usr/local/filebeat/filebeat.yml << 'EOL'
logging.level: info
logging.to_files: true
logging.files:
  path: /var/log/filebeat
  name: filebeat
  keepfiles: 7
  permissions: 0640
EOL
# mkdir /var/log/filebeat

3. Connecting Filebeat to the data processing system

Configure Filebeat to connect to your data processing system. In this case, we'll use Elasticsearch.
To send logs directly to Elasticsearch, edit the Filebeat configuration file and update the output settings section.

Connecting to Elasticsearch 9 requires SSL and authentication.
Verify that you can connect to Elasticsearch on port 9200/tcp (make sure to open port 9200 on the second server beforehand).

# telnet 192.168.11.85 9200

Trying 192.168.11.85...
Connected to 192.168.11.85.
Escape character is '^]'.

① Creating an Elasticsearch CA Certificate
Download the Elasticsearch CA certificate and save it to a directory of your choice (in this example, we'll save it as /usr/local/filebeat/elastic-ca.crt).

# openssl s_client -connect 192.168.11.85:9200 \
-showcerts </dev/null 2>/dev/null | \
openssl x509 -outform PEM > /usr/local/filebeat/elastic-ca.crt

➁Retrieve the credentials that Filebeat uses for Elasticsearch authentication
In this example, we'll use the credentials for the default super administrator, the "Elastic" user.

# vi /usr/local//filebeat/filebeat.yml

Around line 138, add the following to the Kibana section:
#host: "localhost:5601"
host: "192.168.11.85:5601"

Comment out the line around line 164, and add the "Elasticsearch Output" section below it as shown below
output.elasticsearch:
  # Array of hosts to connect to.
  #hosts: ["localhost:9200"]
  hosts: ["192.168.11.85:9200"]

Uncomment around line 171 and add the location of the Elasticsearch CA certificate.
  # Protocol - either `http` (default) or `https`.
  protocol: "https"
  ssl.certificate_authorities: ["/usr/local/filebeat/elastic-ca.crt"]

Uncomment the line around line 175,76 and enter the password.
  # Authentication credentials - either API key or username/password.
  #api_key: "id:api_key"
  username: "elastic"
  password: "Password"   ←The Elastic password created on the second server

➂Configuration File Test

# filebeat test config
Config OK

④Testing Filebeat's Output Connections

#/usr/local/filbeat/filebeat test output

elasticsearch: https://192.168.11.85:9200...
  parse url... OK
  connection...
    parse host... OK
    dns lookup... OK
    addresses: 192.168.11.85
    dial up... OK
  TLS...
    security: server's certificate chain verification is enabled
    handshake... OK
    TLS version: TLSv1.3
    dial up... OK
  talk to server... OK
  version: 8.19.12

⑤Enable the Suricata module in Filebeat

When you enable the Suricata module, /usr/local/filebeat/modules.d/suricata.yml.disabled becomes /usr/local/filebeat/modules.d/suricata.yml, but the contents remain unchanged, so modify it as follows:

# /usr/local/filebeat/filebeat modules enable suricata

# vi /usr/local/filebeat/modules.d/suricata.yml
Change lines 7–8 as follows
- module: suricata
  # All logs
  eve:
    enabled: true
    var.paths: ["/var/log/suricata/eve.json"]

⑥Set Up the Initial Environment
Load the SIEM dashboard into Elasticsearch

# /usr/local/filebeat/filebeat setup -e

{"log.level":"info","@timestamp":"2026-09-19T11:11:44.170+0900","log.logger":"modules","log.origin":{"function":"github.com/elastic/beats/v7/filebeat/fileset.LoadPipeline","file.name":"fileset/pipelines.go","file.line":134},"message":"Elasticsearch pipeline loaded.","service.name":"filebeat","pipeline":"filebeat-9.5.4-suricata-eve-pipeline","ecs.version":"1.6.0"}
{"log.level":"info","@timestamp":"2026-09-19T11:11:44.173+0900","log.logger":"modules","log.origin":{"function":"github.com/elastic/beats/v7/filebeat/fileset.LoadPipeline","file.name":"fileset/pipelines.go","file.line":134},"message":"Elasticsearch pipeline loaded.","service.name":"filebeat","pipeline":"filebeat-9.5.4-suricata-eve-dns","ecs.version":"1.6.0"}
{"log.level":"info","@timestamp":"2026-09-19T11:11:44.175+0900","log.logger":"modules","log.origin":{"function":"github.com/elastic/beats/v7/filebeat/fileset.LoadPipeline","file.name":"fileset/pipelines.go","file.line":134},"message":"Elasticsearch pipeline loaded.","service.name":"filebeat","pipeline":"filebeat-9.5.4-suricata-eve-dns-answer-v1","ecs.version":"1.6.0"}
{"log.level":"info","@timestamp":"2026-09-19T11:11:44.177+0900","log.logger":"modules","log.origin":{"function":"github.com/elastic/beats/v7/filebeat/fileset.LoadPipeline","file.name":"fileset/pipelines.go","file.line":134},"message":"Elasticsearch pipeline loaded.","service.name":"filebeat","pipeline":"filebeat-9.5.4-suricata-eve-dns-answer-v2","ecs.version":"1.6.0"}
{"log.level":"info","@timestamp":"2026-09-19T11:11:44.180+0900","log.logger":"modules","log.origin":{"function":"github.com/elastic/beats/v7/filebeat/fileset.LoadPipeline","file.name":"fileset/pipelines.go","file.line":134},"message":"Elasticsearch pipeline loaded.","service.name":"filebeat","pipeline":"filebeat-9.5.4-suricata-eve-tls","ecs.version":"1.6.0"}
{"log.level":"info","@timestamp":"2026-09-19T11:11:44.182+0900","log.logger":"modules","log.origin":{"function":"github.com/elastic/beats/v7/filebeat/fileset.LoadPipeline","file.name":"fileset/pipelines.go","file.line":134},"message":"Elasticsearch pipeline loaded.","service.name":"filebeat","pipeline":"filebeat-9.5.4-suricata-eve-http","ecs.version":"1.6.0"}

⑦Start the Filebeat service

# /usr/local/filebeat/filebeat

⑩Check in Kibana

Log back into Kibana.
Accesess http://192.168.11.85:5601

Type "Suricata Events Overview" into the top search field, then click [Filebeat Suricata] Events Overview.

The rest of the process is the same as on other operating systems, so I'll skip it.