Merge branch '2.4' of github.com:MISP/MISP into 2.4

pull/3658/head
iglocska 2018-09-09 15:39:32 +02:00
commit 55fe130385
28 changed files with 4731 additions and 4097 deletions

View File

@ -177,10 +177,9 @@ sudo python3 setup.py install
-----------
# CakePHP is included as a submodule of MISP, execute the following commands to let git fetch it:
cd /usr/local/www/MISP
sudo -u www git submodule init
sudo -u www git submodule update
sudo -u www git submodule update --init --recursive
# Make git ignore filesystem permission differences for submodules
sudo -u www git submodule foreach git config core.filemode false
sudo -u www git submodule foreach --recursive git config core.filemode false
# Once done, install CakeResque along with its dependencies if you intend to use the built in background jobs:
cd /usr/local/www/MISP/app

View File

@ -272,10 +272,9 @@ doas pip3.6 install stix2
```
# CakePHP is included as a submodule of MISP, execute the following commands to let git fetch it:
cd /var/www/htdocs/MISP
doas -u www git submodule init
doas -u www git submodule update
doas -u www git submodule update --init --recursive
# Make git ignore filesystem permission differences for submodules
doas -u www git submodule foreach git config core.filemode false
doas -u www git submodule foreach --recursive git config core.filemode false
# Once done, install CakeResque along with its dependencies if you intend to use the built in background jobs:
cd /var/www/htdocs/MISP/app

View File

@ -162,10 +162,9 @@ cd $PATH_TO_MISP/app/files/scripts/mixbox
sudo pip3 install .
cd $PATH_TO_MISP
sudo -u www-data git submodule init
sudo -u www-data git submodule update
sudo -u www-data git submodule update --init --recursive
# Make git ignore filesystem permission differences for submodules
sudo -u www-data git submodule foreach git config core.filemode false
sudo -u www-data git submodule foreach --recursive git config core.filemode false
# install PyMISP
cd $PATH_TO_MISP/PyMISP
@ -678,8 +677,7 @@ sudo apt-get install -y libssl-dev swig python3-ssdeep p7zip-full unrar-free sql
sudo pip3 install SQLAlchemy PrettyTable python-magic
sudo git clone https://github.com/viper-framework/viper.git
cd viper
sudo git submodule init
sudo git submodule update
sudo git submodule update --init --recursive
sudo pip3 install -r requirements.txt
sudo pip3 uninstall yara -y
/usr/local/src/viper/viper-cli -h

View File

@ -174,10 +174,9 @@ cd $PATH_TO_MISP/app/files/scripts/mixbox
sudo pip3 install .
cd $PATH_TO_MISP
sudo -u www-data git submodule init
sudo -u www-data git submodule update
sudo -u www-data git submodule update --init --recursive
# Make git ignore filesystem permission differences for submodules
sudo -u www-data git submodule foreach git config core.filemode false
sudo -u www-data git submodule foreach --recursive git config core.filemode false
# install PyMISP
cd $PATH_TO_MISP/PyMISP
@ -701,8 +700,7 @@ sudo apt-get install -y libssl-dev swig python3-ssdeep p7zip-full unrar-free sql
sudo pip3 install SQLAlchemy PrettyTable python-magic
sudo git clone https://github.com/viper-framework/viper.git
cd viper
sudo git submodule init
sudo git submodule update
sudo git git submodule update --init --recursive
sudo pip3 install -r requirements.txt
sudo pip3 uninstall yara -y
/usr/local/src/viper/viper-cli -h

View File

@ -149,10 +149,9 @@ function installMISPonKali() {
pip3 install .
cd $PATH_TO_MISP
$SUDO_WWW git submodule init
$SUDO_WWW git submodule update
$SUDO_WWW git submodule update --init --recursive
# Make git ignore filesystem permission differences for submodules
$SUDO_WWW git submodule foreach git config core.filemode false
$SUDO_WWW git submodule foreach --recursive git config core.filemode false
# install PyMISP
cd $PATH_TO_MISP/PyMISP
@ -515,8 +514,7 @@ function installMISPonKali() {
git clone https://github.com/viper-framework/viper.git
chown -R $MISP_USER:$MISP_USER viper
cd viper
$SUDO git submodule init
$SUDO git submodule update
$SUDO git submodule update --init --recursive
pip3 install -r requirements.txt
pip3 uninstall yara -y
$SUDO /usr/local/src/viper/viper-cli -h > /dev/null

View File

@ -152,10 +152,9 @@ systemctl restart rh-php71-php-fpm.service
4.01/ CakePHP is now included as a submodule of MISP, execute the following commands to let git fetch it ignore this
message: No submodule mapping found in .gitmodules for path 'app/Plugin/CakeResque'
cd /var/www/MISP
git submodule init
git submodule update
git submodule update --init --recursive
# Make git ignore filesystem permission differences for submodules
git submodule foreach git config core.filemode false
git submodule foreach --recursive git config core.filemode false
4.02/ Install CakeResque along with its dependencies if you intend to use the built in background jobs
cd /var/www/MISP/app

View File

@ -56,10 +56,9 @@ sudo mkdir /var/www/MISP
sudo chown www-data:www-data /var/www/MISP
cd /var/www/MISP
sudo -u www-data git clone https://github.com/MISP/MISP.git /var/www/MISP
sudo -u www-data git submodule init
sudo -u www-data git submodule update
sudo -u www-data git submodule update --init --recursive
# Make git ignore filesystem permission differences for submodules
sudo -u www-data git submodule foreach git config core.filemode false
sudo -u www-data git submodule foreach --recursive git config core.filemode false
# Make git ignore filesystem permission differences
sudo -u www-data git config core.filemode false

View File

@ -80,11 +80,10 @@ git checkout tags/$(git describe --tags `git rev-list --tags --max-count=1`)
# the message regarding a "detached HEAD state" is expected behaviour
# (you only have to create a new branch, if you want to change stuff and do a pull request for example)
git submodule init
git submodule update
git submodule update --init --recursive
# Make git ignore filesystem permission differences
git submodule foreach git config core.filemode false
git submodule foreach --recursive git config core.filemode false
# install Mitre's STIX and its dependencies by running the following commands:
sudo apt-get install python3-dev python3-pip libxml2-dev libxslt1-dev zlib1g-dev python-setuptools python-pip

12
INSTALL/README.md Normal file
View File

@ -0,0 +1,12 @@
Main INSTALL Documentation for the MISP Project.
Currently the following install guides are being tested on a regular basis:
```
INSTALL.debian9.txt
INSTALL.debian_testing.txt
INSTALL.kali.txt
INSTALL.ubuntu1804.txt
```
Install guides with the 'x' prefix, are marked as Experimental.

View File

@ -115,10 +115,9 @@ umask $UMASK
# No submodule mapping found in .gitmodules for path 'app/Plugin/CakeResque'
cd /var/www/MISP
git submodule init
git submodule update
git submodule update --init --recursive
# Make git ignore filesystem permission differences for submodules
git submodule foreach git config core.filemode false
git submodule foreach --recursive git config core.filemode false
# Once done, install CakeResque along with its dependencies if you intend to use the built in background jobs:
cd /var/www/MISP/app

View File

@ -1,6 +1,64 @@
INSTALLATION INSTRUCTIONS
------------------------- for CentOS 7.x
0/ MISP CentOS 7 Minimal NetInstall - Status
--------------------------------------------
Maintained and tested by @SteveClement, CentOS 7.5-1804 on 20180906
CentOS 7.5-1804 NetInstallURL: http://mirror.centos.org/centos/7.5.1804/os/x86_64/
Some configurables used below:
```
# CentOS Specific
RUN_PHP='/usr/bin/scl enable rh-php56 '
RUN_PYTHON='/usr/bin/scl enable rh-python36 '
# MISP configuration variables
PATH_TO_MISP='/var/www/MISP'
CAKE="$PATH_TO_MISP/app/Console/cake"
MISP_BASEURL=''
MISP_LIVE='1'
# Database configuration
DBHOST='localhost'
DBNAME='misp'
DBUSER_ADMIN='root'
DBPASSWORD_ADMIN="$(openssl rand -hex 32)"
DBUSER_MISP='misp'
DBPASSWORD_MISP="$(openssl rand -hex 32)"
# Webserver configuration
FQDN='localhost'
# OpenSSL configuration
OPENSSL_CN='Common Name'
OPENSSL_C='LU'
OPENSSL_ST='State'
OPENSSL_L='Location'
OPENSSL_O='Organization'
OPENSSL_OU='Organizational Unit'
OPENSSL_EMAILADDRESS='info@localhost'
# GPG configuration
GPG_REAL_NAME='Autogenerated Key'
GPG_COMMENT='WARNING: MISP AutoGenerated Key consider this Key VOID!'
GPG_EMAIL_ADDRESS='admin@admin.test'
GPG_KEY_LENGTH='2048'
GPG_PASSPHRASE='Password1234'
# php.ini configuration
upload_max_filesize=50M
post_max_size=50M
max_execution_time=300
memory_limit=512M
PHP_INI=/etc/opt/rh/rh-php56/php.ini
echo "Admin (root) DB Password: $DBPASSWORD_ADMIN"
echo "User (misp) DB Password: $DBPASSWORD_MISP"
```
1/ Minimal CentOS install
-------------------------
@ -11,178 +69,199 @@ Install a minimal CentOS 7.x system with the software:
- Mail server
# Make sure you set your hostname CORRECTLY vs. like an animal (manually in /etc/hostname)
hostnamectl set-hostname misp # or whatever you want it to be
hostnamectl set-hostname misp.local # or whatever you want it to be
# Make sure your system is up2date:
yum update
sudo yum update -y
2/ Dependencies *
----------------
Once the system is installed you can perform the following steps as root:
Once the system is installed you can perform the following steps as root or with sudo:
# We need some packages from the Extra Packages for Enterprise Linux repository
yum install epel-release
sudo yum install epel-release -y
# Since MISP 2.4 PHP 5.5 is a minimal requirement, so we need a newer version than CentOS base provides
# Software Collections is a way do to this, see https://wiki.centos.org/AdditionalResources/Repositories/SCL
yum install centos-release-scl
sudo yum install centos-release-scl -y
# Install the dependencies:
yum install gcc git httpd zip redis mariadb mariadb-server python-devel python-pip libxslt-devel zlib-devel
sudo yum install gcc git httpd zip redis mariadb mariadb-server python-devel python-pip libxslt-devel zlib-devel -y
# Install PHP 5.6 from SCL, see https://www.softwarecollections.org/en/scls/rhscl/rh-php56/
yum install rh-php56 rh-php56-php-fpm rh-php56-php-devel rh-php56-php-mysqlnd rh-php56-php-mbstring rh-php56-php-xml rh-php56-php-bcmath rh-php56-php-opcache
sudo yum install rh-php56 rh-php56-php-fpm rh-php56-php-devel rh-php56-php-mysqlnd rh-php56-php-mbstring rh-php56-php-xml rh-php56-php-bcmath rh-php56-php-opcache -y
# Install Python 3.6 from SCL, see
# https://www.softwarecollections.org/en/scls/rhscl/rh-python36/
yum install rh-python36
sudo yum install rh-python36 -y
# rh-php56-php only provided mod_php for httpd24-httpd from SCL
# if we want to use httpd from CentOS base we can use rh-php56-php-fpm instead
systemctl enable rh-php56-php-fpm.service
systemctl start rh-php56-php-fpm.service
sudo systemctl enable rh-php56-php-fpm.service
sudo systemctl start rh-php56-php-fpm.service
# Start a new shell with rh-php56 enabled
scl enable rh-php56 bash
$RUN_PHP "pear channel-update pear.php.net"
sudo $RUN_PHP "pear install Crypt_GPG" # we need version >1.3.0
pear channel-update pear.php.net
pear install Crypt_GPG # we need version >1.3.0
NOTE: if using rh-php56 the command needs to be run through its terminal: /usr/bin/scl enable rh-php56 "pear list | grep Crypt_GPG"
NOTE: $RUN_PHP makes php available for you if using rh-php56. e.g: $RUN_PHP "pear list | grep Crypt_GPG"
# GPG needs lots of entropy, haveged provides entropy
yum install haveged
systemctl enable haveged.service
systemctl start haveged.service
sudo yum install haveged -y
sudo systemctl enable haveged.service
sudo systemctl start haveged.service
# Enable and start redis
systemctl enable redis.service
systemctl start redis.service
sudo systemctl enable redis.service
sudo systemctl start redis.service
3/ MISP code
------------
# Download MISP using git in the /var/www/ directory.
cd /var/www/
git clone https://github.com/MISP/MISP.git
sudo git clone https://github.com/MISP/MISP.git
cd /var/www/MISP
git checkout tags/$(git describe --tags `git rev-list --tags --max-count=1`)
sudo git checkout tags/$(git describe --tags `git rev-list --tags --max-count=1`)
# if the last shortcut doesn't work, specify the latest version manually
# example: git checkout tags/v2.4.XY
# the message regarding a "detached HEAD state" is expected behaviour
# (you only have to create a new branch, if you want to change stuff and do a pull request for example)
# Make git ignore filesystem permission differences
git config core.filemode false
sudo git config core.filemode false
# Start new shell with python 3 enabled
scl enable rh-python36 bash
# Fetch submodules
cd /var/www/MISP
sudo git submodule update --init --recursive
# Make git ignore filesystem permission differences for submodules
sudo git submodule foreach --recursive git config core.filemode false
# install Mitre's STIX and its dependencies by running the following commands:
yum install python-importlib python-lxml python-dateutil python-six
sudo yum install python-importlib python-lxml python-dateutil python-six -y
cd /var/www/MISP/app/files/scripts
git clone https://github.com/CybOXProject/python-cybox.git
git clone https://github.com/STIXProject/python-stix.git
sudo git clone https://github.com/CybOXProject/python-cybox.git
sudo git clone https://github.com/STIXProject/python-stix.git
cd /var/www/MISP/app/files/scripts/python-cybox
git config core.filemode false
sudo git config core.filemode false
# If you umask is has been changed from the default, it is a good idea to reset it to 0022 before installing python modules
UMASK=$(umask)
umask 0022
python3 setup.py install
sudo $RUN_PYTHON "python3 setup.py install"
cd /var/www/MISP/app/files/scripts/python-stix
git config core.filemode false
python3 setup.py install
sudo git config core.filemode false
sudo $RUN_PYTHON "python3 setup.py install"
# install mixbox to accomodate the new STIX dependencies:
cd /var/www/MISP/app/files/scripts/
git clone https://github.com/CybOXProject/mixbox.git
sudo git clone https://github.com/CybOXProject/mixbox.git
cd /var/www/MISP/app/files/scripts/mixbox
git config core.filemode false
python3 setup.py install
sudo git config core.filemode false
sudo $RUN_PYTHON "python3 setup.py install"
# install PyMISP
cd /var/www/MISP/PyMISP
python3 setup.py install
sudo $RUN_PYTHON "python3 setup.py install"
# Enable python3 for php-fpm
echo 'source scl_source enable rh-python36' >> /etc/opt/rh/rh-php56/sysconfig/php-fpm
sed -i.org -e 's/^;\(clear_env = no\)/\1/' /etc/opt/rh/rh-php56/php-fpm.d/www.conf
systemctl restart rh-php56-php-fpm.service
echo 'source scl_source enable rh-python36' | sudo tee -a /etc/opt/rh/rh-php56/sysconfig/php-fpm
sudo sed -i.org -e 's/^;\(clear_env = no\)/\1/' /etc/opt/rh/rh-php56/php-fpm.d/www.conf
sudo systemctl restart rh-php56-php-fpm.service
umask $UMASK
4/ CakePHP
-----------
# CakePHP is now included as a submodule of MISP, execute the following commands to let git fetch it
# ignore this message:
# No submodule mapping found in .gitmodules for path 'app/Plugin/CakeResque'
cd /var/www/MISP
git submodule init
git submodule update
# Make git ignore filesystem permission differences for submodules
git submodule foreach git config core.filemode false
# Once done, install CakeResque along with its dependencies if you intend to use the built in background jobs:
# CakePHP is now included as a submodule of MISP and has been fetch by a previous step.
# Install CakeResque along with its dependencies if you intend to use the built in background jobs:
sudo chown -R apache:apache /var/www/MISP
sudo mkdir /usr/share/httpd/.composer
sudo chown apache:apache /usr/share/httpd/.composer
cd /var/www/MISP/app
php composer.phar require kamisama/cake-resque:4.1.2
php composer.phar config vendor-dir Vendor
php composer.phar install
sudo -u apache $RUN_PHP "php composer.phar require kamisama/cake-resque:4.1.2"
sudo -u apache $RUN_PHP "php composer.phar config vendor-dir Vendor"
sudo -u apache $RUN_PHP "php composer.phar install"
# CakeResque normally uses phpredis to connect to redis, but it has a (buggy) fallback connector through Redisent. It is highly advised to install phpredis using "yum install php-redis"
pecl install redis-2.2.8
echo "extension=redis.so" > /etc/opt/rh/rh-php56/php-fpm.d/redis.ini
ln -s ../php-fpm.d/redis.ini /etc/opt/rh/rh-php56/php.d/99-redis.ini
systemctl restart rh-php56-php-fpm.service
Note: if using rh-php56 redis needs to be installed through its terminal: /usr/bin/scl enable rh-php56 "pecl install redis-2.2.8"
sudo $RUN_PHP "pecl install redis-2.2.8"
echo "extension=redis.so" |sudo tee /etc/opt/rh/rh-php56/php-fpm.d/redis.ini
sudo ln -s ../php-fpm.d/redis.ini /etc/opt/rh/rh-php56/php.d/99-redis.ini
sudo systemctl restart rh-php56-php-fpm.service
# If you have not yet set a timezone in php.ini
echo 'date.timezone = "Europe/Amsterdam"' > /etc/opt/rh/rh-php56/php-fpm.d/timezone.ini
ln -s ../php-fpm.d/timezone.ini /etc/opt/rh/rh-php56/php.d/99-timezone.ini
echo 'date.timezone = "Europe/Luxembourg"' |sudo tee /etc/opt/rh/rh-php56/php-fpm.d/timezone.ini
sudo ln -s ../php-fpm.d/timezone.ini /etc/opt/rh/rh-php56/php.d/99-timezone.ini
# Recommended: Change some PHP settings in /etc/opt/rh/rh-php56/php.ini
# max_execution_time = 300
# memory_limit = 512M
# upload_max_filesize = 50M
# post_max_size = 50M
for key in upload_max_filesize post_max_size max_execution_time max_input_time memory_limit
do
sudo sed -i "s/^\($key\).*/\1 = $(eval echo \${$key})/" $PHP_INI
done
sudo systemctl restart rh-php56-php-fpm.service
# To use the scheduler worker for scheduled tasks, do the following:
cp -fa /var/www/MISP/INSTALL/setup/config.php /var/www/MISP/app/Plugin/CakeResque/Config/config.php
sudo cp -fa /var/www/MISP/INSTALL/setup/config.php /var/www/MISP/app/Plugin/CakeResque/Config/config.php
5/ Set the permissions
----------------------
# Make sure the permissions are set correctly using the following commands as root:
chown -R root:apache /var/www/MISP
find /var/www/MISP -type d -exec chmod g=rx {} \;
chmod -R g+r,o= /var/www/MISP
chown apache:apache /var/www/MISP/app/files
chown apache:apache /var/www/MISP/app/files/terms
chown apache:apache /var/www/MISP/app/files/scripts/tmp
chown apache:apache /var/www/MISP/app/Plugin/CakeResque/tmp
chown -R apache:apache /var/www/MISP/app/tmp
chown -R apache:apache /var/www/MISP/app/webroot/img/orgs
chown -R apache:apache /var/www/MISP/app/webroot/img/custom
sudo chown -R root:apache /var/www/MISP
sudo find /var/www/MISP -type d -exec chmod g=rx {} \;
sudo chmod -R g+r,o= /var/www/MISP
sudo chmod -R 750 /var/www/MISP
sudo chmod -R g+ws /var/www/MISP/app/tmp
sudo chmod -R g+ws /var/www/MISP/app/files
sudo chmod -R g+ws /var/www/MISP/app/files/scripts/tmp
sudo chown apache:apache /var/www/MISP/app/files
sudo chown apache:apache /var/www/MISP/app/files/terms
sudo chown apache:apache /var/www/MISP/app/files/scripts/tmp
sudo chown apache:apache /var/www/MISP/app/Plugin/CakeResque/tmp
sudo chown -R apache:apache /var/www/MISP/app/Config
sudo chown -R apache:apache /var/www/MISP/app/tmp
sudo chown -R apache:apache /var/www/MISP/app/webroot/img/orgs
sudo chown -R apache:apache /var/www/MISP/app/webroot/img/custom
6/ Create a database and user
-----------------------------
# Enable, start and secure your mysql database server
systemctl enable mariadb.service
systemctl start mariadb.service
mysql_secure_installation
sudo systemctl enable mariadb.service
sudo systemctl start mariadb.service
# If you want to continue copy pasting set the MySQL root password to $DBPASSWORD_ADMIN
echo $DBPASSWORD_ADMIN
sudo mysql_secure_installation
# Additionally, it is probably a good idea to make the database server listen on localhost only
echo [mysqld] > /etc/my.cnf.d/bind-address.cnf
echo bind-address=127.0.0.1 >> /etc/my.cnf.d/bind-address.cnf
systemctl restart mariadb.service
echo [mysqld] |sudo tee /etc/my.cnf.d/bind-address.cnf
echo bind-address=127.0.0.1 |sudo tee -a /etc/my.cnf.d/bind-address.cnf
sudo systemctl restart mariadb.service
# Enter the mysql shell
mysql -u root -p
```
MariaDB [(none)]> create database misp;
MariaDB [(none)]> grant usage on *.* to misp@localhost identified by 'XXXXXXXXX';
MariaDB [(none)]> grant all privileges on misp.* to misp@localhost ;
MariaDB [(none)]> exit
```
cd /var/www/MISP
copy/paste:
```
sudo mysql -u $DBUSER_ADMIN -p$DBPASSWORD_ADMIN -e "create database $DBNAME;"
sudo mysql -u $DBUSER_ADMIN -p$DBPASSWORD_ADMIN -e "grant usage on *.* to $DBNAME@localhost identified by '$DBPASSWORD_MISP';"
sudo mysql -u $DBUSER_ADMIN -p$DBPASSWORD_ADMIN -e "grant all privileges on $DBNAME.* to '$DBUSER_MISP'@'localhost';"
sudo mysql -u $DBUSER_ADMIN -p$DBPASSWORD_ADMIN -e "flush privileges;"
```
# Import the empty MySQL database from MYSQL.sql
mysql -u misp -p misp < INSTALL/MYSQL.sql
sudo -u apache cat $PATH_TO_MISP/INSTALL/MYSQL.sql | mysql -u $DBUSER_MISP -p$DBPASSWORD_MISP $DBNAME
7/ Apache configuration
@ -190,59 +269,82 @@ mysql -u misp -p misp < INSTALL/MYSQL.sql
# Now configure your apache server with the DocumentRoot /var/www/MISP/app/webroot/
# A sample vhost can be found in /var/www/MISP/INSTALL/apache.misp.centos7
cp /var/www/MISP/INSTALL/apache.misp.centos7 /etc/httpd/conf.d/misp.conf
sudo cp /var/www/MISP/INSTALL/apache.misp.centos7 /etc/httpd/conf.d/misp.conf
# Since SELinux is enabled, we need to allow httpd to write to certain directories
chcon -t httpd_sys_rw_content_t /var/www/MISP/app/files
chcon -t httpd_sys_rw_content_t /var/www/MISP/app/files/terms
chcon -t httpd_sys_rw_content_t /var/www/MISP/app/files/scripts/tmp
chcon -t httpd_sys_rw_content_t /var/www/MISP/app/Plugin/CakeResque/tmp
chcon -R -t httpd_sys_rw_content_t /var/www/MISP/app/tmp
chcon -R -t httpd_sys_rw_content_t /var/www/MISP/app/webroot/img/orgs
chcon -R -t httpd_sys_rw_content_t /var/www/MISP/app/webroot/img/custom
sudo chcon -t httpd_sys_rw_content_t /var/www/MISP/app/files
sudo chcon -t httpd_sys_rw_content_t /var/www/MISP/app/files/terms
sudo chcon -t httpd_sys_rw_content_t /var/www/MISP/app/files/scripts/tmp
sudo chcon -t httpd_sys_rw_content_t /var/www/MISP/app/Plugin/CakeResque/tmp
sudo chcon -R -t httpd_sys_rw_content_t /var/www/MISP/app/tmp
sudo chcon -R -t httpd_sys_rw_content_t /var/www/MISP/app/tmp/logs
sudo chcon -R -t httpd_sys_rw_content_t /var/www/MISP/app/webroot/img/orgs
sudo chcon -R -t httpd_sys_rw_content_t /var/www/MISP/app/webroot/img/custom
# Allow httpd to connect to the redis server and php-fpm over tcp/ip
setsebool -P httpd_can_network_connect on
sudo setsebool -P httpd_can_network_connect on
# Enable and start the httpd service
systemctl enable httpd.service
systemctl start httpd.service
sudo systemctl enable httpd.service
sudo systemctl start httpd.service
# Open a hole in the iptables firewall
firewall-cmd --zone=public --add-port=80/tcp --permanent
firewall-cmd --reload
sudo firewall-cmd --zone=public --add-port=80/tcp --permanent
sudo firewall-cmd --reload
# We seriously recommend using only HTTPS / SSL !
# Add SSL support by running: yum install mod_ssl
# Check out the apache.misp.ssl file for an example
/!\ WARNING - To be fixed - Place holder
# If a valid SSL certificate is not already created for the server, create a self-signed certificate:
sudo openssl req -newkey rsa:4096 -days 365 -nodes -x509 \
-subj "/C=${OPENSSL_C}/ST=${OPENSSL_ST}/L=${OPENSSL_L}/O=${OPENSSL_O}/OU=${OPENSSL_OU}/CN=${OPENSSL_CN}/emailAddress=${OPENSSL_EMAILADDRESS}" \
-keyout /etc/ssl/private/misp.local.key -out /etc/ssl/private/misp.local.crt
8/ Log rotation
---------------
# MISP saves the stdout and stderr of it's workers in /var/www/MISP/app/tmp/logs
# To rotate these logs install the supplied logrotate script:
cp INSTALL/misp.logrotate /etc/logrotate.d/misp
chmod 0640 /etc/logrotate.d/misp
sudo cp $PATH_TO_MISP/INSTALL/misp.logrotate /etc/logrotate.d/misp
sudo chmod 0640 /etc/logrotate.d/misp
# Now make logrotate work under SELinux as well
# Allow logrotate to modify the log files
semanage fcontext -a -t httpd_log_t "/var/www/MISP/app/tmp/logs(/.*)?"
chcon -R -t httpd_log_t /var/www/MISP/app/tmp/logs
sudo semanage fcontext -a -t httpd_log_t "/var/www/MISP/app/tmp/logs(/.*)?"
sudo chcon -R -t httpd_log_t /var/www/MISP/app/tmp/logs
# Allow logrotate to read /var/www
checkmodule -M -m -o /tmp/misplogrotate.mod INSTALL/misplogrotate.te
semodule_package -o /tmp/misplogrotate.pp -m /tmp/misplogrotate.mod
semodule -i /tmp/misplogrotate.pp
sudo checkmodule -M -m -o /tmp/misplogrotate.mod $PATH_TO_MISP/INSTALL/misplogrotate.te
sudo semodule_package -o /tmp/misplogrotate.pp -m /tmp/misplogrotate.mod
sudo semodule -i /tmp/misplogrotate.pp
9/ MISP configuration
---------------------
# There are 4 sample configuration files in /var/www/MISP/app/Config that need to be copied
cd /var/www/MISP/app/Config
cp -a bootstrap.default.php bootstrap.php
cp -a database.default.php database.php
cp -a core.default.php core.php
cp -a config.default.php config.php
# There are 4 sample configuration files in $PATH_TO_MISP/app/Config that need to be copied
sudo -u apache cp -a $PATH_TO_MISP/app/Config/bootstrap.default.php $PATH_TO_MISP/app/Config/bootstrap.php
sudo -u apache cp -a $PATH_TO_MISP/app/Config/database.default.php $PATH_TO_MISP/app/Config/database.php
sudo -u apache cp -a $PATH_TO_MISP/app/Config/core.default.php $PATH_TO_MISP/app/Config/core.php
sudo -u apache cp -a $PATH_TO_MISP/app/Config/config.default.php $PATH_TO_MISP/app/Config/config.php
echo "<?php
class DATABASE_CONFIG {
public \$default = array(
'datasource' => 'Database/Mysql',
//'datasource' => 'Database/Postgres',
'persistent' => false,
'host' => '$DBHOST',
'login' => '$DBUSER_MISP',
'port' => 3306, // MySQL & MariaDB
//'port' => 5432, // PostgreSQL
'password' => '$DBPASSWORD_MISP',
'database' => '$DBNAME',
'prefix' => '',
'encoding' => 'utf8',
);
}" | sudo -u apache tee $PATH_TO_MISP/app/Config/database.php
# Configure the fields in the newly created files:
# config.php : baseurl (example: 'baseurl' => 'http://misp',) - don't use "localhost" it causes issues when browsing externally
@ -270,31 +372,174 @@ cp -a config.default.php config.php
# delete the user from mysql and log in again using the default admin credentials (admin@admin.test / admin)
# If you want to be able to change configuration parameters from the webinterface:
chown apache:apache /var/www/MISP/app/Config/config.php
chcon -t httpd_sys_rw_content_t /var/www/MISP/app/Config/config.php
sudo chown apache:apache /var/www/MISP/app/Config/config.php
sudo chcon -t httpd_sys_rw_content_t /var/www/MISP/app/Config/config.php
# Set some MISP directives with the command line tool
sudo $RUN_PHP "$CAKE Live $MISP_LIVE"
# Change base url
sudo $RUN_PHP "$CAKE Baseurl $MISP_BASEURL"
# Generate a GPG encryption key.
# If the following command gives an error message, try it as root from the console
gpg --gen-key
mv ~/.gnupg /var/www/MISP/
chown -R apache:apache /var/www/MISP/.gnupg
cat >/tmp/gen-key-script <<EOF
%echo Generating a default key
Key-Type: default
Key-Length: $GPG_KEY_LENGTH
Subkey-Type: default
Name-Real: $GPG_REAL_NAME
Name-Comment: $GPG_COMMENT
Name-Email: $GPG_EMAIL_ADDRESS
Expire-Date: 0
Passphrase: $GPG_PASSPHRASE
# Do a commit here, so that we can later print "done"
%commit
%echo done
EOF
# The email address should match the one set in the config.php configuration file
# Make sure that you use the same settings in the MISP Server Settings tool (Described on line 246)
sudo gpg --homedir /var/www/MISP/.gnupg --batch --gen-key /tmp/gen-key-script
sudo rm -f /tmp/gen-key-script
sudo chown -R apache:apache /var/www/MISP/.gnupg
# And export the public key to the webroot
sudo -u apache gpg --homedir /var/www/MISP/.gnupg --export --armor YOUR-EMAIL > /var/www/MISP/app/webroot/gpg.asc
sudo gpg --homedir /var/www/MISP/.gnupg --export --armor $GPG_EMAIL_ADDRESS |sudo tee /var/www/MISP/app/webroot/gpg.asc
sudo chown apache:apache /var/www/MISP/app/webroot/gpg.asc
# Start the workers to enable background jobs
chmod +x /var/www/MISP/app/Console/worker/start.sh
su -s /bin/bash apache -c 'scl enable rh-php56 /var/www/MISP/app/Console/worker/start.sh'
sudo -u apache $RUN_PHP /var/www/MISP/app/Console/worker/start.sh
# To make the background workers start on boot
vi /etc/rc.local
# Add the following line at the end
su -s /bin/bash apache -c 'scl enable rh-php56 /var/www/MISP/app/Console/worker/start.sh'
# and make sure it will execute
chmod +x /etc/rc.local
sudo chmod +x /etc/rc.local
# Initialize user and fetch Auth Key
sudo -E $RUN_PHP "$CAKE userInit -q"
AUTH_KEY=$(mysql -u $DBUSER_MISP -p$DBPASSWORD_MISP misp -e "SELECT authkey FROM users;" | tail -1)
# Setup some more MISP default via cake CLI
# Tune global time outs
sudo $RUN_PHP "$CAKE Admin setSetting "Session.autoRegenerate" 0"
sudo $RUN_PHP "$CAKE Admin setSetting "Session.timeout" 600"
sudo $RUN_PHP "$CAKE Admin setSetting "Session.cookie_timeout" 3600"
# Enable GnuPG
sudo $RUN_PHP "$CAKE Admin setSetting "GnuPG.email" "admin@admin.test""
sudo $RUN_PHP "$CAKE Admin setSetting "GnuPG.homedir" "$PATH_TO_MISP/.gnupg""
sudo $RUN_PHP "$CAKE Admin setSetting "GnuPG.password" "Password1234""
# Enable Enrichment set better timeouts
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Enrichment_services_enable" true"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Enrichment_hover_enable" true"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Enrichment_timeout" 300"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Enrichment_hover_timeout" 150"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Enrichment_cve_enabled" true"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Enrichment_dns_enabled" true"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Enrichment_services_url" "http://127.0.0.1""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Enrichment_services_port" 6666"
# Enable Import modules set better timout
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Import_services_enable" true"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Import_services_url" "http://127.0.0.1""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Import_services_port" 6666"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Import_timeout" 300"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Import_ocr_enabled" true"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Import_csvimport_enabled" true"
# Enable Export modules set better timout
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Export_services_enable" true"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Export_services_url" "http://127.0.0.1""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Export_services_port" 6666"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Export_timeout" 300"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Export_pdfexport_enabled" true"
# Enable installer org and tune some configurables
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.host_org_id" 1"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.email" "info@admin.test""
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.disable_emailing" true"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.contact" "info@admin.test""
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.disablerestalert" true"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.showCorrelationsOnIndex" true"
# Provisional Cortex tunes
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Cortex_services_enable" false"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Cortex_services_url" "http://127.0.0.1""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Cortex_services_port" 9000"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Cortex_timeout" 120"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Cortex_services_url" "http://127.0.0.1""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Cortex_services_port" 9000"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Cortex_services_timeout" 120"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Cortex_services_authkey" """
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Cortex_ssl_verify_peer" false"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Cortex_ssl_verify_host" false"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Cortex_ssl_allow_self_signed" true"
# Various plugin sightings settings
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Sightings_policy" 0"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Sightings_anonymise" false"
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.Sightings_range" 365"
# Plugin CustomAuth tuneable
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.CustomAuth_disable_logout" false"
# RPZ Plugin settings
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.RPZ_policy" "DROP""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.RPZ_walled_garden" "127.0.0.1""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.RPZ_serial" "\$date00""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.RPZ_refresh" "2h""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.RPZ_retry" "30m""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.RPZ_expiry" "30d""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.RPZ_minimum_ttl" "1h""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.RPZ_ttl" "1w""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.RPZ_ns" "localhost.""
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.RPZ_ns_alt" """
sudo $RUN_PHP "$CAKE Admin setSetting "Plugin.RPZ_email" "root.localhost""
# Force defaults to make MISP Server Settings less RED
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.language" "eng""
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.proposals_block_attributes" false"
## Redis block
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.redis_host" "127.0.0.1""
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.redis_port" 6379"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.redis_database" 13"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.redis_password" """
# Force defaults to make MISP Server Settings less YELLOW
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.ssdeep_correlation_threshold" 40"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.extended_alert_subject" false"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.default_event_threat_level" 4"
##sudo $RUN_PHP "$CAKE Admin setSetting "MISP.newUserText" "Dear new MISP user,\\n\\nWe would hereby like to welcome you to the \$org MISP community.\\n\\n Use the credentials below to log into MISP at \$misp, where you will be prompted to manually change your password to something of your own choice.\\n\\nUsername: \$username\\nPassword: \$password\\n\\nIf you have any questions, don't hesitate to contact us at: \$contact.\\n\\nBest regards,\\nYour \$org MISP support team""
##sudo $CAKE Admin setSetting "MISP.passwordResetText" "Dear MISP user,\\n\\nA password reset has been triggered for your account. Use the below provided temporary password to log into MISP at \$misp, where you will be prompted to manually change your password to something of your own choice.\\n\\nUsername: \$username\\nYour temporary password: \$password\\n\\nIf you have any questions, don't hesitate to contact us at: \$contact.\\n\\nBest regards,\\nYour \$org MISP support team""
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.enableEventBlacklisting" true"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.enableOrgBlacklisting" true"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.log_client_ip" false"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.log_auth" false"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.disableUserSelfManagement" false"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.block_event_alert" false"
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.block_event_alert_tag" "no-alerts=\"true\"""
sudo $RUN_PHP "$CAKE Admin setSetting "MISP.block_old_event_alert" false"
##sudo $RUN_PHP "$CAKE Admin setSetting "MISP.block_old_event_alert_age" """
##sudo $RUN_PHP "$CAKE Admin setSetting "MISP.incoming_tags_disabled_by_default" false"
##sudo $RUN_PHP "$CAKE Admin setSetting "MISP.footermidleft" "This is an initial install""
##sudo $RUN_PHP "$CAKE Admin setSetting "MISP.footermidright" "Please configure and harden accordingly""
##sudo $RUN_PHP "$CAKE Admin setSetting "MISP.welcome_text_top" "Initial Install, please configure""
##sudo $RUN_PHP "$CAKE Admin setSetting "MISP.welcome_text_bottom" "Welcome to MISP, change this message in MISP Settings""
# Force defaults to make MISP Server Settings less GREEN
sudo $RUN_PHP "$CAKE Admin setSetting "Security.password_policy_length" 12"
##sudo $RUN_PHP "$CAKE Admin setSetting "Security.password_policy_complexity" '/^((?=.*\d)|(?=.*\W+))(?![\n])(?=.*[A-Z])(?=.*[a-z]).*$|.{16,}/'"
# Tune global time outs
sudo $RUN_PHP "$CAKE Admin setSetting "Session.autoRegenerate" 0"
sudo $RUN_PHP "$CAKE Admin setSetting "Session.timeout" 600"
sudo $RUN_PHP "$CAKE Admin setSetting "Session.cookie_timeout" 3600"
# Now log in using the webinterface: http://misp/users/login
# The default user/pass = admin@admin.test/admin

View File

@ -2096,7 +2096,8 @@ class AttributesController extends AppController
'xml' => array('xml', 'XmlExport'),
'suricata' => array('txt', 'NidsSuricataExport'),
'snort' => array('txt', 'NidsSnortExport'),
'text' => array('txt', 'TextExport')
'text' => array('txt', 'TextExport'),
'rpz' => array('rpz', 'RPZExport')
);
$exception = false;
$filters = $this->_harvestParameters($filterData, $exception);
@ -2133,7 +2134,7 @@ class AttributesController extends AppController
'enforceWarninglist' => !empty($filters['enforceWarninglist']) ? $filters['enforceWarninglist'] : 0,
'includeAllTags' => true,
'flatten' => 1,
'includeEventUuid' => !empty($filters['includeEventUuid']) ? $filters['includeEventUuid'] : 0,
'includeEventUuid' => !empty($filters['includeEventUuid']) ? $filters['includeEventUuid'] : 0
);
if (!empty($filtes['deleted'])) {
$params['deleted'] = 1;
@ -2150,7 +2151,8 @@ class AttributesController extends AppController
'user' => $this->Auth->user(),
'params' => $params,
'returnFormat' => $returnFormat,
'scope' => 'Attribute'
'scope' => 'Attribute',
'filters' => $filters
);
if (!empty($exportTool->additional_params)) {
$params = array_merge($params, $exportTool->additional_params);
@ -2158,7 +2160,7 @@ class AttributesController extends AppController
$final = $exportTool->header($exportToolParams);
$continue = false;
if (empty($params['limit'])) {
$params['limit'] = 10000;
$params['limit'] = 20000;
$continue = true;
$params['page'] = 1;
}
@ -2400,7 +2402,7 @@ class AttributesController extends AppController
if (isset($data['request'][$p])) {
${$p} = $data['request'][$p];
} else {
${$p} = null;
${$p} = false;
}
}
}
@ -2452,7 +2454,7 @@ class AttributesController extends AppController
throw new UnauthorizedException(__('You have to be logged in to do that.'));
}
}
if (false === $eventId) {
if (false === $eventId || $eventId === null) {
$eventIds = $this->Attribute->Event->fetchEventIds($this->Auth->user(), false, false, false, true);
} elseif (is_numeric($eventId)) {
$eventIds = array($eventId);

View File

@ -1739,13 +1739,14 @@ class EventsController extends AppController
throw new UnauthorizedException(__('You do not have permission to do that.'));
}
if ($this->request->is('post')) {
$original_file = !empty($this->data['Event']['original_file']) ? $this->data['Event']['stix']['name'] : None;
if ($this->_isRest()) {
$randomFileName = $this->Event->generateRandomFileName();
$tmpDir = APP . "files" . DS . "scripts" . DS . "tmp";
$tempFile = new File($tmpDir . DS . $randomFileName, true, 0644);
$tempFile->write($this->request->input());
$tempFile->close();
$result = $this->Event->upload_stix($this->Auth->user(), $randomFileName, $stix_version);
$result = $this->Event->upload_stix($this->Auth->user(), $randomFileName, $stix_version, $original_file);
if (is_array($result)) {
return $this->RestResponse->saveSuccessResponse('Events', 'upload_stix', false, $this->response->type(), 'STIX document imported, event\'s created: ' . implode(', ', $result) . '.');
} elseif (is_numeric($result)) {
@ -1763,7 +1764,7 @@ class EventsController extends AppController
$randomFileName = $this->Event->generateRandomFileName();
$tmpDir = APP . "files" . DS . "scripts" . DS . "tmp";
move_uploaded_file($this->data['Event']['stix']['tmp_name'], $tmpDir . DS . $randomFileName);
$result = $this->Event->upload_stix($this->Auth->user(), $randomFileName, $stix_version);
$result = $this->Event->upload_stix($this->Auth->user(), $randomFileName, $stix_version, $original_file);
if (is_array($result)) {
$this->Flash->success(__('STIX document imported, event\'s created: ' . implode(', ', $result) . '.'));
$this->redirect(array('action' => 'index'));
@ -3023,7 +3024,8 @@ class EventsController extends AppController
'json' => array('json', 'JsonExport'),
'xml' => array('xml', 'XmlExport'),
'suricata' => array('txt', 'NidsSuricataExport'),
'snort' => array('txt', 'NidsSnortExport')
'snort' => array('txt', 'NidsSnortExport'),
'rpz' => array('rpz', 'RPZExport')
);
$exception = false;
$filters = $this->_harvestParameters($filterData, $exception);
@ -3053,7 +3055,8 @@ class EventsController extends AppController
'user' => $this->Auth->user(),
'params' => array(),
'returnFormat' => $returnFormat,
'scope' => 'Event'
'scope' => 'Event',
'filters' => $filters
);
if (empty($exportTool->non_restrictive_export)) {
if (!isset($filters['to_ids'])) {

View File

@ -25,6 +25,117 @@ class RPZExport
),
);
private $__items = array();
public $additional_params = array(
'flatten' => 1
);
private $__rpzSettings = array();
private $__valid_policies = array('NXDOMAIN', 'NODATA', 'DROP', 'walled-garden');
private $__server = null;
public $validTypes = array(
'ip-src' => array(
'value' => 'ip'
),
'ip-dst' => array(
'value' => 'ip'
),
'domain' => array(
'value' => 'domain'
),
'domain|ip' => array(
'value1' => 'domain',
'value2' => 'ip'
),
'hostname' => array(
'value' => 'hostname'
)
);
public function handler($data, $options = array())
{
if ($options['scope'] === 'Attribute') {
return $this->__attributeHandler($data, $options);
} else {
return $this->__eventHandler($data, $options);
}
}
private function __eventHandler($event, $options = array()) {
foreach ($event['Attribute'] as $attribute) {
if (isset($this->validTypes[$attribute['type']])) {
if ($attribute['type'] == 'domain|ip') {
$temp = explode('|', $attribute['value']);
$attribute['value1'] = $temp[0];
$attribute['value2'] = $temp[1];
}
$this->__attributeHandler(array('Attribute' => $attribute, $options));
}
}
return '';
}
private function __attributeHandler($attribute, $options = array())
{
if (isset($attribute['Attribute'])) {
$attribute = $attribute['Attribute'];
}
if (isset($this->validTypes[$attribute['type']])) {
foreach ($this->validTypes[$attribute['type']] as $field => $mapping) {
// get rid of the in_array check
if (empty($this->__items[$mapping]) || !isset($this->__items[$mapping][$attribute[$field]])) {
$this->__items[$mapping][$attribute[$field]] = true;
}
}
}
return '';
}
public function header($options = array())
{
$lookupData = array('policy', 'walled_garden', 'ns', 'ns_alt', 'email', 'serial', 'refresh', 'retry', 'expiry', 'minimum_ttl', 'ttl');
foreach ($lookupData as $v) {
if ($v === 'policy' && isset($options['filters'][$v])) {
if (!in_array($options['filters'][$v], array('NXDOMAIN', 'NODATA', 'DROP', 'walled-garden'))) {
unset($options['filters'][$v]);
} else {
$options['filters'][$v] = $this->getIdByPolicy($options['filters'][$v]);
}
}
if (isset($options['filters'][$v])) {
$this->__rpzSettings[$v] = $options['filters'][$v];
} else {
$tempSetting = Configure::read('Plugin.RPZ_' . $v);
if (isset($tempSetting)) {
$this->__rpzSettings[$v] = Configure::read('Plugin.RPZ_' . $v);
} else {
if (empty($this->__server)) {
$this->__server = ClassRegistry::init('Server');
}
$this->__rpzSettings[$v] = $this->__server->serverSettings['Plugin']['RPZ_' . $v]['value'];
}
}
}
return '';
}
public function footer($options = array())
{
foreach ($this->__items as $k => $v) {
$this->__items[$k] = array_keys($this->__items[$k]);
}
return $this->export($this->__items, $this->__rpzSettings);
}
public function separator()
{
return '';
}
public function getPolicyById($id)
{
foreach ($this->__policies as $k => $v) {
@ -61,7 +172,7 @@ class RPZExport
$header = '';
$header .= '$TTL ' . $rpzSettings['ttl'] . ';' . PHP_EOL;
$header .= '@ SOA ' . $rpzSettings['ns'] . ' ' . $rpzSettings['email'] . ' (' . $rpzSettings['serial'] . ' ' . $rpzSettings['refresh'] . ' ' . $rpzSettings['retry'] . ' ' . $rpzSettings['expiry'] . ' ' . $rpzSettings['minimum_ttl'] . ')' . PHP_EOL;
if (!empty($rpzSettings['ns_alt'])) {
$header .= ' NS ' . $rpzSettings['ns'] . PHP_EOL;
$header .= ' NS ' . $rpzSettings['ns_alt'] . PHP_EOL . PHP_EOL;

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -2230,7 +2230,8 @@ class Attribute extends AppModel
array(
'conditions' => $tempConditions,
'fields' => array('Attribute.value'), // array of field names
'enforceWarninglist' => $enforceWarninglist
'enforceWarninglist' => $enforceWarninglist,
'flatten' => 1
)
);
if (empty($temp)) {
@ -3401,7 +3402,6 @@ class Attribute extends AppModel
));
} else {
$tags = array();
if (isset($attribute['AttributeTag'])) {
foreach ($attribute['AttributeTag'] as $at) {
unset($at['id']);

View File

@ -4743,7 +4743,7 @@ class Event extends AppModel
return $this->save($event);
}
public function upload_stix($user, $filename, $stix_version)
public function upload_stix($user, $filename, $stix_version, $original_file)
{
App::uses('Folder', 'Utility');
App::uses('File', 'Utility');
@ -4760,7 +4760,7 @@ class Event extends AppModel
} else {
throw new MethodNotAllowedException('Invalid STIX version');
}
$shell_command .= ' ' . escapeshellarg(Configure::read('MISP.default_event_distribution')) . ' ' . escapeshellarg(Configure::read('MISP.default_attribute_distribution')) . ' 2>' . APP . 'tmp/logs/exec-errors.log';
$shell_command .= ' ' . $original_file . ' ' . escapeshellarg(Configure::read('MISP.default_event_distribution')) . ' ' . escapeshellarg(Configure::read('MISP.default_attribute_distribution')) . ' 2>' . APP . 'tmp/logs/exec-errors.log';
$result = shell_exec($shell_command);
unlink($tempFilePath);
if (trim($result) == '1') {

View File

@ -1812,8 +1812,6 @@ class Server extends AppModel
$eventIds = array_intersect($eventIds, $local_event_ids);
} elseif (is_numeric($technique)) {
$eventIds[] = intval($technique);
// if we are downloading a single event, don't fetch all proposals
$conditions = array('Event.id' => $technique);
} else {
return array('error' => array(4, null));
}
@ -1832,7 +1830,7 @@ class Server extends AppModel
return false;
}
private function __updatePulledEventBeforeInsert($event, $server, $user)
private function __updatePulledEventBeforeInsert(&$event, $server, $user)
{
// we have an Event array
// The event came from a pull, so it should be locked.
@ -1870,10 +1868,9 @@ class Server extends AppModel
return $event;
}
private function __checkIfPulledEventExistsAndAddOrUpdate($event, &$successes, &$fails, $eventModel, $server, $user, $passAlong, $job, $jobId)
private function __checkIfPulledEventExistsAndAddOrUpdate($event, $eventId, &$successes, &$fails, $eventModel, $server, $user, $jobId)
{
// check if the event already exist (using the uuid)
$existingEvent = null;
$existingEvent = $eventModel->find('first', array('conditions' => array('Event.uuid' => $event['Event']['uuid'])));
if (!$existingEvent) {
// add data for newly imported events
@ -1898,7 +1895,7 @@ class Server extends AppModel
}
}
private function __pullEvents($eventId, $successes, $fails, $eventModel, $server, $user, $passAlong, $job, $jobId)
private function __pullEvent($eventId, &$successes, &$fails, $eventModel, $server, $user, $jobId)
{
$event = $eventModel->downloadEventFromServer(
$eventId,
@ -1909,21 +1906,15 @@ class Server extends AppModel
return false;
}
$this->__updatePulledEventBeforeInsert($event, $server, $user);
$this->__checkIfPulledEventExistsAndAddOrUpdate($event, $successes, $fails, $eventModel, $server, $user, $passAlong, $job, $jobId);
$this->__checkIfPulledEventExistsAndAddOrUpdate($event, $eventId, $successes, $fails, $eventModel, $server, $user, $jobId);
} else {
// error
$fails[$eventId] = 'failed downloading the event';
}
if ($jobId) {
if ($k % 10 == 0) {
$job->id = $jobId;
$job->saveField('progress', 50 * (($k + 1) / count($eventIds)));
}
}
return true;
}
private function __handlePulledProposals($proposals, $events, $job, $jobId)
private function __handlePulledProposals($proposals, $events, $job, $jobId, $eventModel, $user)
{
$pulledProposals = array();
if (!empty($proposals)) {
@ -1971,7 +1962,7 @@ class Server extends AppModel
if ($jobId) {
if ($k % 50 == 0) {
$job->id = $jobId;
$job->saveField('progress', 50 * (($k + 1) / count($proposals)));
$job->saveField('progress', 50 * (($k + 1) / count($proposals)) + 50);
}
}
}
@ -1979,7 +1970,7 @@ class Server extends AppModel
return $pulledProposals;
}
public function pull($user, $id = null, $technique=false, $server, $jobId = false, $percent = 100, $current = 0)
public function pull($user, $id = null, $technique=false, $server, $jobId = false)
{
if ($jobId) {
$job = ClassRegistry::init('Job');
@ -1990,9 +1981,9 @@ class Server extends AppModel
$email = $user['email'];
}
$eventModel = ClassRegistry::init('Event');
App::uses('HttpSocket', 'Network/Http');
$eventIds = array();
$conditions = array();
// if we are downloading a single event, don't fetch all proposals
$conditions = is_numeric($technique) ? array('Event.id' => $technique) : array();
$eventIds = $this->__getEventIdListBasedOnPullTechnique($technique, $server);
if (!empty($eventIds['error'])) {
$errors = array(
@ -2020,9 +2011,13 @@ class Server extends AppModel
// now process the $eventIds to pull each of the events sequentially
if (!empty($eventIds)) {
// download each event
$HttpSocket = $this->setupHttpSocket($server);
foreach ($eventIds as $k => $eventId) {
$this->__pullEvents($eventId, $successes, $fails, $eventModel, $server, $user, $passAlong, $job, $jobId);
$this->__pullEvent($eventId, $successes, $fails, $eventModel, $server, $user, $jobId);
if ($jobId) {
if ($k % 10 == 0) {
$job->saveField('progress', 50 * (($k + 1) / count($eventIds)));
}
}
}
}
if ($jobId) {
@ -2035,7 +2030,7 @@ class Server extends AppModel
));
if (!empty($events)) {
$proposals = $eventModel->downloadProposalsFromServer($events, $server);
$pulledProposals = $this->__handlePulledProposals($proposals, $events, $job, $jobId);
$pulledProposals = $this->__handlePulledProposals($proposals, $events, $job, $jobId, $eventModel, $user);
}
if ($jobId) {
$job->saveField('progress', 100);

View File

@ -96,6 +96,7 @@ class Sighting extends AppModel
$sighting['org_id'] = $org_id;
$sighting['event_id'] = $event_id;
$sighting['attribute_id'] = $attribute_id;
$this->create();
return $this->save($sighting);
}

View File

@ -2,22 +2,29 @@
<?php
echo $this->Form->create('Event', array('type' => 'file'));
?>
<fieldset>
<legend><?php echo __('Import %s file', $stix_version); ?></legend>
<fieldset>
<legend><?php echo __('Import %s file', $stix_version); ?></legend>
<?php
echo $this->Form->input('Event.stix', array(
'label' => '<b>' . __('%s file', $stix_version) . '</b>',
'type' => 'file',
));
?>
<div class="input clear"></div>
<?php
?>
<div class="input clear"></div>
<?php
echo $this->Form->input('publish', array(
'checked' => false,
'label' => __('Publish imported events'),
));
?>
</fieldset>
<div class="input clear"></div>
<?php
echo $this->Form->input('original_file', array(
'checked' => true,
'label' => __('Include the original imported file as attachment')
));
?>
</fieldset>
<?php
echo $this->Form->button(__('Upload'), array('class' => 'btn btn-primary'));
echo $this->Form->end();

@ -1 +1 @@
Subproject commit 38071f4bd9e3de1138a096cbbf66089f5105d798
Subproject commit bb2b8d810fa2f34f9b32aebe37bcc3bfa750e43a

View File

@ -23,6 +23,7 @@ import time
import uuid
import io
import stix2
from base64 import b64encode
from pymisp import MISPEvent, MISPObject, __path__
from stix2misp_mapping import *
from collections import defaultdict
@ -43,7 +44,7 @@ class StixParser():
with open(filename, 'r', encoding='utf-8') as f:
event = json.loads(f.read())
self.filename = filename
self.stix_version = 'stix {}'.format(event.get('spec_version'))
self.stix_version = 'STIX {}'.format(event.get('spec_version'))
for o in event.get('objects'):
parsed_object = stix2.parse(o, allow_custom=True)
try:
@ -57,14 +58,16 @@ class StixParser():
if not self.event:
print(json.dumps({'success': 0, 'message': 'There is no valid STIX object to import'}))
sys.exit(1)
if args[2] is not None:
self.add_original_file(args[2])
try:
event_distribution = args[2]
event_distribution = args[3]
if not isinstance(event_distribution, int):
event_distribution = int(event_distribution) if event_distribution.isdigit() else 5
except IndexError:
event_distribution = 5
try:
attribute_distribution = args[3]
attribute_distribution = args[4]
if attribute_distribution != 'event' and not isinstance(attribute_distribution, int):
attribute_distribution = int(attribute_distribution) if attribute_distribution.isdigit() else 5
except IndexError:
@ -73,6 +76,16 @@ class StixParser():
self.__attribute_distribution = event_distribution if attribute_distribution == 'event' else attribute_distribution
self.load_mapping()
def add_original_file(self, original_filename):
with open(self.filename, 'rb') as f:
sample = b64encode(f.read()).decode('utf-8')
original_file = MISPObject('original-imported-file')
original_file.add_attribute(**{'type': 'attachment', 'value': original_filename,
'object_relation': 'imported-sample', 'data': sample})
original_file.add_attribute(**{'type': 'text', 'object_relation': 'format',
'value': self.stix_version})
self.misp_event.add_object(**original_file)
def load_mapping(self):
self.objects_mapping = {'asn': {'observable': observable_asn, 'pattern': pattern_asn},
'domain-ip': {'observable': observable_domain_ip, 'pattern': pattern_domain_ip},

View File

@ -20,6 +20,7 @@ import json
import os
import time
import uuid
import base64
import stix2misp_mapping
from operator import attrgetter
from pymisp import MISPEvent, MISPObject, MISPAttribute, __path__
@ -54,9 +55,10 @@ class StixParser():
try:
import maec
print(2)
except ModuleNotFoundError:
except ImportError:
print(3)
sys.exit(0)
self.filename = filename
title = event.stix_header.title
fromMISP = (title is not None and "Export from " in title and "MISP" in title)
if fromMISP:
@ -65,14 +67,16 @@ class StixParser():
self.ttps = package.ttps.ttps if package.ttps else None
else:
self.event = event
if args[2] is not None:
self.add_original_file(args[2])
try:
event_distribution = args[2]
event_distribution = args[3]
if not isinstance(event_distribution, int):
event_distribution = int(event_distribution) if event_distribution.isdigit() else 5
except IndexError:
event_distribution = 5
try:
attribute_distribution = args[3]
attribute_distribution = args[4]
if attribute_distribution != 'event' and not isinstance(attribute_distribution, int):
attribute_distribution = int(attribute_distribution) if attribute_distribution.isdigit() else 5
except IndexError:
@ -80,9 +84,18 @@ class StixParser():
self.misp_event.distribution = event_distribution
self.__attribute_distribution = event_distribution if attribute_distribution == 'event' else attribute_distribution
self.fromMISP = fromMISP
self.filename = filename
self.load_mapping()
def add_original_file(self, original_filename):
with open(self.filename, 'rb') as f:
sample = base64.b64encode(f.read()).decode('utf-8')
original_file = MISPObject('original-imported_file')
original_file.add_attribute(**{'type': 'attachment', 'value': original_filename,
'object_relation': 'imported-sample', 'data': sample})
original_file.add_attribute(**{'type': 'text', 'object_relation': 'format',
'value': 'STIX {}'.format(self.event.version)})
self.misp_event.add_object(**original_file)
# Load the mapping dictionary for STIX object types
def load_mapping(self):
self.attribute_types_mapping = {
@ -465,9 +478,10 @@ class StixParser():
b_file = True
attribute_type, relation = stix2misp_mapping.eventTypes[properties._XSI_TYPE]
attributes.append([attribute_type, value, relation])
self.fetch_attributes_with_keys(properties, stix2misp_mapping._file_mapping, attributes)
attributes.extend(self.fetch_attributes_with_keys(properties, stix2misp_mapping._file_mapping))
if len(attributes) == 1:
return attributes[0]
attribute = attributes[0]
return attribute if attribute[2] != "fullpath" else "filename", attribute[1], ""
if len(attributes) == 2:
if b_hash and b_file:
return self.handle_filename_object(attributes, is_object)
@ -558,7 +572,7 @@ class StixParser():
# Return type & attributes of a network socket objet
def handle_network_socket(self, properties):
attributes = self.fetch_attributes_from_sockets(properties, stix2misp_mapping._network_socket_addresses)
self.fetch_attributes_with_keys(properties, stix2misp_mapping._network_socket_mapping, attributes)
attributes.extend(self.fetch_attributes_with_keys(properties, stix2misp_mapping._network_socket_mapping))
for prop in ('is_listening', 'is_blocking'):
if getattr(properties, prop):
attributes.append(["text", prop.split('_')[1], "state"])
@ -947,11 +961,13 @@ class StixParser():
return attributes
@staticmethod
def fetch_attributes_with_keys(properties, mapping_dict, attributes):
def fetch_attributes_with_keys(properties, mapping_dict):
attributes = []
for prop, mapping in mapping_dict.items():
if getattr(properties,prop):
attribute_type, properties_key, relation = mapping
attributes.append([attribute_type, attrgetter(properties_key)(properties), relation])
return attributes
@staticmethod
def fetch_attributes_with_key_parsing(properties, mapping_dict):

View File

@ -11,6 +11,7 @@ eventTypes = {"ArtifactObjectType": {"type": "attachment", "relation": "attachme
"PDFFileObjectType": _file_attribute_type,
"PortObjectType": {"type": "port", "relation": "port"},
"URIObjectType": {"type": "url", "relation": "url"},
"WindowsFileObjectType": _file_attribute_type,
"WindowsExecutableFileObjectType": _file_attribute_type,
"WindowsRegistryKeyObjectType": {"type": "regkey", "relation": ""}}
@ -30,10 +31,11 @@ _email_mapping = {'from_': ("email-src", "address_value.value", "from"),
'boundary': ("email-mime-boundary", 'value', "mime-boundary"),
'user_agent': ("text", 'value', "user-agent")}
_file_mapping = {'file_path': ('text', 'file_path.value', 'path'),
'file_format': ('mime-type', 'file_format.value', 'mimetype'),
'byte_runs': ('pattern-in-file', 'byte_runs[0].byte_run_data', 'pattern-in-file'),
'size_in_bytes': ('size-in-bytes', 'size_in_bytes.value', 'size-in-bytes'),
'peak_entropy': ('float', 'peak_entropy.value', 'entropy')}
'full_path': ('text', 'full_path.value', 'fullpath'),
'file_format': ('mime-type', 'file_format.value', 'mimetype'),
'byte_runs': ('pattern-in-file', 'byte_runs[0].byte_run_data', 'pattern-in-file'),
'size_in_bytes': ('size-in-bytes', 'size_in_bytes.value', 'size-in-bytes'),
'peak_entropy': ('float', 'peak_entropy.value', 'entropy')}
_network_socket_mapping = {'protocol': ('text', 'protocol.value', 'protocol'),
'address_family': ('text', 'address_family.value', 'address-family'),
'domain': ('text', 'domain.value', 'domain-family')}