Updated armband
[armband.git] / patches / fuel-plugin-opendaylight / 0001-ODL-leveldb-leveldbjni-Enable-arm64-support.patch
1 From: Florin Dumitrascu <florin.dumitrascu@enea.com>
2 Date: Thu, 17 Mar 2016 18:15:42 +0100
3 Subject: [PATCH] ODL leveldb, leveldbjni: Enable arm64 support.
4
5 ODL depends on a native library (leveldb).
6
7 ODL Beryllium and Boron versions are still using a native x86 version
8 of this library (wrapped in leveldbjni).
9
10 There is no upstream version of leveldbjni supporting arm64 leveldb,
11 so we need to compile it when deploying ODL.
12 This is done when running odl-install puppet manifest.
13
14 For more info about this ODL limitation, see [1].
15
16 [1] https://bugs.opendaylight.org/show_bug.cgi?id=3973
17
18 [ Alexandru.Avadanii@enea.com ]
19 Remove JAVA8 changes after upstream rework.
20
21 Signed-off-by: Florin Dumitrascu <florin.dumitrascu@enea.com>
22 Signed-off-by: Stanislaw Kardach <stanislaw.kardach@cavium.com>
23 Signed-off-by: Alexandru Avadanii <Alexandru.Avadanii@enea.com>
24 ---
25  .../modules/opendaylight/files/leveldb-arm64.patch |  35 +++++
26  .../opendaylight/files/leveldbjni-native.patch     |  23 ++++
27  .../puppet/modules/opendaylight/manifests/init.pp  |   8 ++
28  .../modules/opendaylight/manifests/install.pp      |  12 +-
29  .../modules/opendaylight/manifests/leveldbjni.pp   | 150 +++++++++++++++++++++
30  deployment_tasks.yaml                              |   2 +-
31  6 files changed, 227 insertions(+), 3 deletions(-)
32  create mode 100644 deployment_scripts/puppet/modules/opendaylight/files/leveldb-arm64.patch
33  create mode 100644 deployment_scripts/puppet/modules/opendaylight/files/leveldbjni-native.patch
34  create mode 100644 deployment_scripts/puppet/modules/opendaylight/manifests/leveldbjni.pp
35
36 diff --git a/deployment_scripts/puppet/modules/opendaylight/files/leveldb-arm64.patch b/deployment_scripts/puppet/modules/opendaylight/files/leveldb-arm64.patch
37 new file mode 100644
38 index 0000000..e0824ca
39 --- /dev/null
40 +++ b/deployment_scripts/puppet/modules/opendaylight/files/leveldb-arm64.patch
41 @@ -0,0 +1,35 @@
42 +diff --git a/port/atomic_pointer.h b/port/atomic_pointer.h
43 +index e17bf43..78cb6b3 100644
44 +--- a/port/atomic_pointer.h
45 ++++ b/port/atomic_pointer.h
46 +@@ -36,6 +36,8 @@
47 + #define ARCH_CPU_X86_FAMILY 1
48 + #elif defined(__ARMEL__)
49 + #define ARCH_CPU_ARM_FAMILY 1
50 ++#elif defined(__aarch64__)
51 ++#define ARCH_CPU_ARM64_FAMILY 1
52 + #elif defined(__ppc__) || defined(__powerpc__) || defined(__powerpc64__)
53 + #define ARCH_CPU_PPC_FAMILY 1
54 + #endif
55 +@@ -93,6 +95,13 @@ inline void MemoryBarrier() {
56 + }
57 + #define LEVELDB_HAVE_MEMORY_BARRIER
58 +
59 ++// ARM64
60 ++#elif defined(ARCH_CPU_ARM64_FAMILY)
61 ++inline void MemoryBarrier() {
62 ++ asm volatile("dmb sy" : : : "memory");
63 ++}
64 ++#define LEVELDB_HAVE_MEMORY_BARRIER
65 ++
66 + // PPC
67 + #elif defined(ARCH_CPU_PPC_FAMILY) && defined(__GNUC__)
68 + inline void MemoryBarrier() {
69 +@@ -216,6 +225,7 @@ class AtomicPointer {
70 + #undef LEVELDB_HAVE_MEMORY_BARRIER
71 + #undef ARCH_CPU_X86_FAMILY
72 + #undef ARCH_CPU_ARM_FAMILY
73 ++#undef ARCH_CPU_ARM64_FAMILY
74 + #undef ARCH_CPU_PPC_FAMILY
75 +
76 + }  // namespace port
77 diff --git a/deployment_scripts/puppet/modules/opendaylight/files/leveldbjni-native.patch b/deployment_scripts/puppet/modules/opendaylight/files/leveldbjni-native.patch
78 new file mode 100644
79 index 0000000..08a528b
80 --- /dev/null
81 +++ b/deployment_scripts/puppet/modules/opendaylight/files/leveldbjni-native.patch
82 @@ -0,0 +1,23 @@
83 +diff --git a/leveldbjni-all/pom.xml b/leveldbjni-all/pom.xml
84 +index 426f2a6..c4a2a16 100755
85 +--- a/leveldbjni-all/pom.xml
86 ++++ b/leveldbjni-all/pom.xml
87 +@@ -41,7 +41,7 @@
88 +
89 +   <groupId>org.fusesource.leveldbjni</groupId>
90 +   <artifactId>leveldbjni-all</artifactId>
91 +-  <version>1.8</version>
92 ++  <version>1.8-odl</version>
93 +   <packaging>bundle</packaging>
94 +
95 +   <name>${project.artifactId}</name>
96 +@@ -119,7 +119,8 @@
97 +               META-INF/native/osx/libleveldbjni.jnilib;osname=macosx;processor=x86,
98 +               META-INF/native/osx/libleveldbjni.jnilib;osname=macosx;processor=x86-64,
99 +               META-INF/native/linux32/libleveldbjni.so;osname=Linux;processor=x86,
100 +-              META-INF/native/linux64/libleveldbjni.so;osname=Linux;processor=x86-64
101 ++              META-INF/native/linux64/libleveldbjni.so;osname=Linux;processor=x86-64,
102 ++              META-INF/native/linux64/libleveldbjni.so;osname=Linux;processor=aarch64
103 +             </Bundle-NativeCode>
104 +          </instructions>
105 +         </configuration>
106 diff --git a/deployment_scripts/puppet/modules/opendaylight/manifests/init.pp b/deployment_scripts/puppet/modules/opendaylight/manifests/init.pp
107 index a322f70..f71bfc8 100644
108 --- a/deployment_scripts/puppet/modules/opendaylight/manifests/init.pp
109 +++ b/deployment_scripts/puppet/modules/opendaylight/manifests/init.pp
110 @@ -10,4 +10,12 @@ class opendaylight {
111    $odl_mgmt_ips = values($odl_mgmt_ips_hash)
112    $odl_nodes_names = keys($odl_mgmt_ips_hash)
113    $node_internal_address = $odl_mgmt_ips_hash["node-${node_uid}"]
114 +
115 +  $arch = $::architecture ? {
116 +    'aarch64' => $::osfamily ? {
117 +      'Debian' => 'arm64',
118 +      default  => 'aarch64',
119 +    },
120 +    default => $::architecture,
121 +  }
122  }
123 diff --git a/deployment_scripts/puppet/modules/opendaylight/manifests/install.pp b/deployment_scripts/puppet/modules/opendaylight/manifests/install.pp
124 index 924a840..d55a311 100644
125 --- a/deployment_scripts/puppet/modules/opendaylight/manifests/install.pp
126 +++ b/deployment_scripts/puppet/modules/opendaylight/manifests/install.pp
127 @@ -17,6 +17,12 @@ class opendaylight::install (
128      ensure  => installed,
129    }
130  
131 +  if ($::osfamily == 'Debian' and $::opendaylight::arch == 'arm64') {
132 +    class { 'opendaylight::leveldbjni':
133 +      require => Package[$odl_package],
134 +    }
135 +  }
136 +
137    # quagga
138    class { 'opendaylight::quagga':
139      before => Service['opendaylight']
140 @@ -35,7 +41,8 @@ class opendaylight::install (
141  
142    debug("Set odl rest api port to ${rest_port}")
143  
144 -  file { "${conf_dir}/jetty.xml":
145 +  file { 'jetty.xml':
146 +    path    => "${conf_dir}/jetty.xml",
147      ensure  => file,
148      owner   => 'odl',
149      content => template('opendaylight/jetty.xml.erb')
150 @@ -71,6 +78,7 @@ class opendaylight::install (
151    Package[$odl_package] ->
152    Ini_setting <||> ->
153    Firewall <||> ->
154 -  File <||> ->
155 +  File['jetty.xml'] ->
156 +  Class['opendaylight::leveldbjni'] ->
157    Service['opendaylight']
158  }
159 diff --git a/deployment_scripts/puppet/modules/opendaylight/manifests/leveldbjni.pp b/deployment_scripts/puppet/modules/opendaylight/manifests/leveldbjni.pp
160 new file mode 100644
161 index 0000000..5125fc7
162 --- /dev/null
163 +++ b/deployment_scripts/puppet/modules/opendaylight/manifests/leveldbjni.pp
164 @@ -0,0 +1,150 @@
165 +# == Class opendaylight::leveldbjni
166 +#
167 +# Manages compilation of JNI for leveldb.
168 +#
169 +# It compiles the leveldbjni from sources and patches it so that it's properly
170 +# detected by maven on arm64 system.
171 +#
172 +class opendaylight::leveldbjni(
173 +  $target = '/opt/opendaylight',
174 +  $user    = 'odl',
175 +  $branch  = 'leveldbjni-1.8',
176 +) {
177 +  case $::osfamily {
178 +    'Debian', 'Ubuntu': {}
179 +    default: {
180 +      fail('Not supported on OS other than Debian based.')
181 +    }
182 +  }
183 +
184 +  $libsnappy_dir = '/usr/lib'
185 +  $leveldb_dir = "${target}/leveldb"
186 +  $leveldbjni_dir = "${target}/leveldbjni"
187 +  $environment = ["SNAPPY_HOME=${libsnappy_dir}", "LEVELDB_HOME=${leveldb_dir}", "LEVELDBJNI_HOME=${leveldbjni_dir}", "LIBRARY_PATH=${libsnappy_dir}", "C_INCLUDE_PATH=${libsnappy_dir}", "CPLUS_INCLUDE_PATH=${libsnappy_dir}","JAVA_HOME=/usr/lib/jvm/java-8-openjdk-${::opendaylight::arch}"]
188 +  $parallel_jobs = ($processorcount + 1)/2
189 +
190 +  if ! defined(Package['git']) {
191 +    package { 'git':
192 +      ensure => 'present',
193 +    }
194 +  }
195 +  if ! defined(Package['build-essential']) {
196 +    package { 'build-essential':
197 +      ensure => 'present',
198 +    }
199 +  }
200 +  if ! defined(Package['automake']) {
201 +    package { 'automake':
202 +      ensure => 'present',
203 +    }
204 +  }
205 +  if ! defined(Package['make']) {
206 +    package { 'make':
207 +      ensure => 'present',
208 +    }
209 +  }
210 +  if ! defined(Package['libsnappy-dev']) {
211 +    package { 'libsnappy-dev':
212 +      ensure => 'present',
213 +    }
214 +  }
215 +  if ! defined(Package['patch']) {
216 +    package { 'patch':
217 +      ensure => 'present',
218 +    }
219 +  }
220 +  if ! defined(Package['maven']) {
221 +    package { 'maven':
222 +      ensure => 'present',
223 +    }
224 +  }
225 +  if ! defined(Package['openjdk-8-jdk']) {
226 +    package { 'openjdk-8-jdk':
227 +      ensure => 'present',
228 +    }
229 +  }
230 +
231 +  exec { 'leveldb-fetch':
232 +    path    => ['/usr/bin'],
233 +    command => "git clone git://github.com/chirino/leveldb.git ${leveldb_dir}",
234 +    creates => "${leveldb_dir}/.git",
235 +    user    => $user,
236 +    require => [Package['git']],
237 +  } ->
238 +  exec { 'leveldbjni-fetch':
239 +    path    => ['/usr/bin'],
240 +    command => "git clone https://github.com/fusesource/leveldbjni.git -b ${branch} ${leveldbjni_dir}",
241 +    creates => "${leveldbjni_dir}/.git",
242 +    user    => $user,
243 +    require => [Package['git']],
244 +  } ->
245 +  exec { 'leveldb-merge-google':
246 +    path    => ['/usr/bin', '/bin'],
247 +    command => "git config user.name odl && git config user.email 'o@d.l' && git remote add google https://github.com/google/leveldb.git && git fetch google master && git fetch --tags google && git merge --no-edit v1.18",
248 +    unless  => "git remote | grep google",
249 +    cwd     => $leveldb_dir,
250 +    user    => $user,
251 +    require => [Package['git']],
252 +  } ->
253 +  exec { 'leveldb-patch':
254 +    path    => ['/usr/bin'],
255 +    command => "patch -p1 < ${leveldbjni_dir}/leveldb.patch",
256 +    unless  => "patch -p1 -R -N --dry-run < ${leveldbjni_dir}/leveldb.patch",
257 +    cwd     => $leveldb_dir,
258 +    user    => $user,
259 +    require => [Package['patch']],
260 +  } ->
261 +  file { "${leveldb_dir}/leveldb-arm64.patch":
262 +    ensure => "file",
263 +    source => "puppet:///modules/opendaylight/leveldb-arm64.patch",
264 +    owner  => $user,
265 +  } ->
266 +  exec { 'leveldb-patch-for-arm64':
267 +    path    => ['/usr/bin'],
268 +    command => "patch -p1 < ${leveldb_dir}/leveldb-arm64.patch",
269 +    unless  => "patch -p1 -R -N --dry-run < ${leveldb_dir}/leveldb-arm64.patch",
270 +    cwd     => $leveldb_dir,
271 +    user    => $user,
272 +    require => [Package['patch']],
273 +  } ->
274 +  exec { 'leveldb-build':
275 +    command => "/usr/bin/make libleveldb.a -j${parallel_jobs}",
276 +    creates => "${leveldb_dir}/libleveldb.a",
277 +    environment => $environment,
278 +    cwd     => $leveldb_dir,
279 +    user    => $user,
280 +    require => [Package['git'], Package['make'], Package['build-essential']],
281 +  } ->
282 +  file { "${leveldbjni_dir}/leveldbjni.patch":
283 +    ensure => "file",
284 +    source => "puppet:///modules/opendaylight/leveldbjni-native.patch",
285 +    owner  => $user,
286 +  } ->
287 +  exec { 'leveldbjni-patch':
288 +    path    => ['/usr/bin'],
289 +    command => "patch -p1 < ${leveldbjni_dir}/leveldbjni.patch",
290 +    unless  => "patch -p1 -R -N --dry-run < ${leveldbjni_dir}/leveldbjni.patch",
291 +    cwd     => $leveldbjni_dir,
292 +    user    => $user,
293 +    require => [Package['patch']],
294 +  } ->
295 +  exec { 'leveldbjni-build':
296 +    command     => "/usr/bin/mvn clean install -P download -P linux64 -P all",
297 +    # Creates requires a fully qualified path which we don't have
298 +    unless      => "/usr/bin/test -d ~${user}/.m2/repository/org/fusesource/leveldbjni/leveldbjni-all",
299 +    environment => $environment,
300 +    cwd         => $leveldbjni_dir,
301 +    user        => $user,
302 +    timeout     => 1200,
303 +    require     => [Package['maven']],
304 +  } ->
305 +  # Can't do this with 'file' type because we need to purge existing package
306 +  # and at the same time don't perform the copy if we've already copied our
307 +  # package.
308 +  exec { 'leveldbjni-copy':
309 +    path    => ['/bin'],
310 +    command => "rm -rf ${target}/system/org/fusesource/leveldbjni && cp -r ~${user}/.m2/repository/org/fusesource/leveldbjni $target/system/org/fusesource/",
311 +    creates => "${target}/system/org/fusesource/leveldbjni/leveldbjni-linux64",
312 +    user    => $user,
313 +  }
314 +}
315 diff --git a/deployment_tasks.yaml b/deployment_tasks.yaml
316 index 3706678..841bfee 100644
317 --- a/deployment_tasks.yaml
318 +++ b/deployment_tasks.yaml
319 @@ -17,7 +17,7 @@
320    parameters:
321      puppet_manifest: puppet/manifests/odl-install.pp
322      puppet_modules: puppet/modules:/etc/puppet/modules
323 -    timeout: 720
324 +    timeout: 3600
325  - id: netconfig
326    type: puppet
327    version: 2.0.0