meson: Add meson and meson_option files

Tested: compile and run successfully

tests log using run-unit-test-docker.sh :
 1/14 dbus_active_unittest                    OK              0.03s
 2/14 dbus_util_unittest                      OK              0.02s
 3/14 json_parse_unittest                     OK              0.02s
 4/14 pid_json_unittest                       OK              0.02s
 5/14 pid_stepwisecontroller_unittest         OK              0.03s
 6/14 pid_fancontroller_unittest              OK              0.04s
 7/14 pid_thermalcontroller_unittest          OK              0.03s
 8/14 dbus_passive_unittest                   OK              0.05s
 9/14 sensor_pluggable_unittest               OK              0.02s
10/14 sensor_manager_unittest                 OK              0.02s
11/14 sensor_host_unittest                    OK              0.03s
12/14 sensors_json_unittest                   OK              0.01s
13/14 util_unittest                           OK              0.01s
14/14 pid_zone_unittest                       OK              0.04s

Ok:                 14
Expected Fail:      0
Fail:               0
Unexpected Pass:    0
Skipped:            0
Timeout:            0

systemctl status phosphor-pid-control.service
* phosphor-pid-control.service - Phosphor-Pid-Control Margin-based Fan Control Daemon
     Loaded: loaded (/lib/systemd/system/phosphor-pid-control.service; enabled; preset: enabled)
    Drop-In: /lib/systemd/system/phosphor-pid-control.service.d
             `-service-override.conf
     Active: active (running) since Fri 2018-03-09 04:36:30 PST; 1min 37s ago
    Process: 2561 ExecStartPre=/usr/bin/fan-table-init.sh (code=exited, status=0/SUCCESS)
   Main PID: 2633 (swampd)
     CGroup: /system.slice/phosphor-pid-control.service
             `-2633 /usr/bin/swampd

Mar 09 04:36:45 qbmc swampd[2633]: PID name: pwm 5
Mar 09 04:36:45 qbmc swampd[2633]: inputs: fan2_tachfan5_pwm, fan3_tachfan5_pwm, fan5_tachfan5_pwm,
Mar 09 04:36:45 qbmc swampd[2633]: PID name: tray_dt PID
Mar 09 04:36:45 qbmc swampd[2633]: inputs: tray_dt,
Mar 09 04:36:45 qbmc swampd[2633]: pushing zone 2
Mar 09 04:36:45 qbmc swampd[2633]: PID Zone 2 max SetPoint 4200 requested by CPU0 PID fan0_tachfan4_pwm fan1_tachfan4_pwm fan2_tachfan5_pwm fan3_tachfan5_pwm fan4_tachfan4_pwm fan5_tachfan5_pwm
Mar 09 04:36:45 qbmc swampd[2633]: pushing zone 1
Mar 09 04:36:45 qbmc swampd[2633]: PID Zone 1 max SetPoint 4200 requested by CPU1 PID fan2_tachfan2_pwm fan3_tachfan3_pwm
Mar 09 04:36:45 qbmc swampd[2633]: pushing zone 0
Mar 09 04:36:45 qbmc swampd[2633]: PID Zone 0 max SetPoint 4200 requested by CPU0 PID fan0_tachfan0_pwm fan1_tachfan1_pwm

Signed-off-by: Harvey.Wu <Harvey.Wu@quantatw.com>
Change-Id: I779fed7a5deef262a0e65d4eb00116072beb28e8
diff --git a/meson.build b/meson.build
new file mode 100644
index 0000000..8a99aa5
--- /dev/null
+++ b/meson.build
@@ -0,0 +1,152 @@
+project(
+    'phosphor-pid-control', 'cpp',
+    version : '1.0.0',
+    meson_version: '>=0.63.0',
+    default_options: [
+        'warning_level=3',
+        'werror=true',
+        'cpp_std=c++20',
+    ]
+)
+
+conf_data = configuration_data()
+
+bindir = get_option('prefix') / get_option('bindir')
+conf_data.set('BINDIR', bindir)
+conf_data.set('SYSTEMD_TARGET', get_option('systemd_target'))
+conf_data.set('STRICT_FAILSAFE_PWM', get_option('strict-failsafe-pwm'))
+
+configure_file(output: 'config.h',
+    configuration: conf_data
+)
+
+if get_option('oe-sdk').enabled()
+    OECORE_TARGET_SYSROOT = run_command('sh', '-c', 'echo $OECORE_TARGET_SYSROOT').stdout().strip()
+    if OECORE_TARGET_SYSROOT == ''
+        error('OECORE_TARGET_SYSROOT must be set with enable oe-sdk')
+    endif
+    message('Enabling OE-SDK at OECORE_TARGET_SYSROOT: ' + OECORE_TARGET_SYSROOT)
+    rpath = ':'.join([OECORE_TARGET_SYSROOT + '/lib', OECORE_TARGET_SYSROOT + '/usr/lib'])
+    ld_so = run_command('sh', '-c', 'find ' + OECORE_TARGET_SYSROOT + '/lib/ld-*.so | sort -r -n | head -n1').stdout().strip()
+    dynamic_linker = ['-Wl,-dynamic-linker,' + ld_so]
+else
+    dynamic_linker = []
+endif
+
+systemd = dependency('systemd')
+systemd_system_unit_dir = systemd.get_variable(
+        pkgconfig: 'systemdsystemunitdir',
+        pkgconfig_define: ['prefix', get_option('prefix')])
+
+configure_file(input: 'phosphor-pid-control.service.in',
+               output: 'phosphor-pid-control.service',
+               configuration: conf_data,
+               install: true,
+               install_dir: systemd_system_unit_dir)
+
+phosphor_dbus_interfaces_dep = dependency('phosphor-dbus-interfaces')
+phosphor_logging_dep = dependency('phosphor-logging')
+sdbusplus_dep = dependency('sdbusplus')
+libsystemd_dep = dependency('libsystemd')
+ipmid_dep = dependency('libipmid')
+
+deps = [
+    phosphor_dbus_interfaces_dep,
+    phosphor_logging_dep,
+    sdbusplus_dep,
+    libsystemd_dep,
+    ipmid_dep,
+]
+
+root_inc = include_directories(
+    '.',
+    'buildjson',
+    'dbus',
+    'errors',
+    'experiments',
+    'ipmi',
+    'notimpl',
+    'pid',
+    'sensors',
+    'sysfs',
+)
+
+setsensor_sources = [
+    'setsensor.cpp'
+]
+
+libswampd_sources = [
+    'main.cpp',
+    'util.cpp',
+    'notimpl/readonly.cpp',
+    'notimpl/writeonly.cpp',
+    'dbus/dbusconfiguration.cpp',
+    'dbus/dbusutil.cpp',
+    'dbus/dbushelper.cpp',
+    'dbus/dbuspassiveredundancy.cpp',
+    'dbus/dbuspassive.cpp',
+    'dbus/dbusactiveread.cpp',
+    'dbus/dbuswrite.cpp',
+    'sysfs/sysfsread.cpp',
+    'sysfs/sysfswrite.cpp',
+    'sysfs/util.cpp',
+    'sensors/pluggable.cpp',
+    'sensors/host.cpp',
+    'sensors/builder.cpp',
+    'sensors/buildjson.cpp',
+    'sensors/manager.cpp',
+    'sensors/build_utils.cpp',
+    'pid/ec/pid.cpp',
+    'pid/ec/stepwise.cpp',
+    'pid/fancontroller.cpp',
+    'pid/thermalcontroller.cpp',
+    'pid/pidcontroller.cpp',
+    'pid/stepwisecontroller.cpp',
+    'pid/builder.cpp',
+    'pid/buildjson.cpp',
+    'pid/zone.cpp',
+    'pid/util.cpp',
+    'pid/pidloop.cpp',
+    'pid/tuning.cpp',
+    'buildjson/buildjson.cpp',
+    'experiments/drive.cpp',
+]
+
+libmanualcmds_sources = [
+    'ipmi/main_ipmi.cpp',
+    'ipmi/manualcmds.cpp',
+    'ipmi/dbus_mode.cpp',
+]
+
+libmanualcmds = library(
+    'manualcmds',
+    libmanualcmds_sources,
+    implicit_include_directories: false,
+    dependencies: deps,
+    version: meson.project_version(),
+    override_options: ['b_lundef=false'],
+    install: true,
+    install_dir: get_option('libdir') / 'ipmid-providers')
+
+executable(
+    'swampd',
+    libswampd_sources,
+    implicit_include_directories: false,
+    include_directories: root_inc,
+    dependencies: deps,
+    install: true,
+    install_dir: get_option('bindir')
+)
+
+executable(
+    'setsensor',
+    setsensor_sources,
+    implicit_include_directories: true,
+    dependencies: deps,
+    install: true,
+    install_dir: get_option('bindir')
+)
+
+if not get_option('tests').disabled()
+    subdir('test')
+endif
diff --git a/meson_options.txt b/meson_options.txt
new file mode 100644
index 0000000..9655044
--- /dev/null
+++ b/meson_options.txt
@@ -0,0 +1,4 @@
+option('tests', type: 'feature', value: 'disabled', description: 'Build tests')
+option('oe-sdk', type: 'feature', value: 'disabled', description: 'Enable OE SDK')
+option('strict-failsafe-pwm', type: 'boolean', value: false, description: 'Set the fans strictly at the failsafe PWM when in failsafe mode')
+option('systemd_target', type: 'string', value: 'multi-user.target', description: 'Target for starting this service')
diff --git a/test/meson.build b/test/meson.build
new file mode 100644
index 0000000..8963593
--- /dev/null
+++ b/test/meson.build
@@ -0,0 +1,84 @@
+gtest = dependency('gtest', main: true, disabler: true, required: false)
+gmock = dependency('gmock', disabler: true, required: false)
+
+if not gtest.found() or not gmock.found()
+    gtest_proj = import('cmake').subproject('googletest', required: false)
+    if gtest_proj.found()
+        gtest = declare_dependency(
+        dependencies: [
+            dependency('threads'),
+            gtest_proj.dependency('gtest'),
+            gtest_proj.dependency('gtest_main'),
+        ])
+        gmock = gtest_proj.dependency('gmock')
+    else
+        assert(not get_option('tests').enabled(), 'Googletest is required')
+    endif
+endif
+
+swampd_sources = include_directories('../')
+
+unit_tests = [
+    'dbus_active_unittest',
+    'dbus_passive_unittest',
+    'dbus_util_unittest',
+    'json_parse_unittest',
+    'pid_json_unittest',
+    'pid_fancontroller_unittest',
+    'pid_stepwisecontroller_unittest',
+    'pid_thermalcontroller_unittest',
+    'pid_zone_unittest',
+    'sensor_host_unittest',
+    'sensor_manager_unittest',
+    'sensor_pluggable_unittest',
+    'sensors_json_unittest',
+    'util_unittest',
+]
+
+unittest_source = {
+    'dbus_active_unittest': ['../dbus/dbusactiveread.cpp'],
+    'dbus_passive_unittest': ['../dbus/dbuspassive.cpp',
+                              '../dbus/dbuspassiveredundancy.cpp',
+                              '../dbus/dbusutil.cpp'],
+    'dbus_util_unittest': ['../dbus/dbusutil.cpp'],
+    'json_parse_unittest': ['../buildjson/buildjson.cpp'],
+    'pid_json_unittest': ['../pid/buildjson.cpp'],
+    'pid_fancontroller_unittest': ['../pid/ec/pid.cpp',
+                                   '../pid/fancontroller.cpp',
+                                   '../pid/pidcontroller.cpp',
+                                   '../pid/tuning.cpp',
+                                   '../pid/util.cpp'],
+    'pid_stepwisecontroller_unittest': ['../pid/ec/stepwise.cpp',
+                                        '../pid/stepwisecontroller.cpp',
+                                        '../pid/util.cpp'],
+    'pid_thermalcontroller_unittest': ['../pid/ec/pid.cpp',
+                                       '../pid/pidcontroller.cpp',
+                                       '../pid/thermalcontroller.cpp',
+                                       '../pid/tuning.cpp',
+                                       '../pid/util.cpp'],
+    'pid_zone_unittest': ['../pid/ec/pid.cpp',
+                          '../pid/pidcontroller.cpp',
+                          '../pid/tuning.cpp',
+                          '../pid/zone.cpp',
+                          '../sensors/manager.cpp'],
+    'sensor_host_unittest': ['../sensors/host.cpp'],
+    'sensor_manager_unittest': ['../sensors/manager.cpp'],
+    'sensor_pluggable_unittest': ['../sensors/pluggable.cpp'],
+    'sensors_json_unittest': ['../sensors/buildjson.cpp'],
+    'util_unittest': ['../sensors/build_utils.cpp']
+}
+
+foreach t : unit_tests
+    test(t, executable(t.underscorify(), t + '.cpp',
+                       unittest_source.get(t),
+                       include_directories: [
+                           swampd_sources,
+                       ],
+                       link_args: dynamic_linker,
+                       build_rpath: get_option('oe-sdk').enabled() ? rpath : '',
+                       dependencies: [
+                           gtest,
+                           gmock,
+                           deps,
+                       ]))
+endforeach