Skip to content

Instantly share code, notes, and snippets.

@bahamat
Last active August 2, 2020 16:47
Show Gist options
  • Save bahamat/e9cca22830b2a3fdbb3a1a0215dec672 to your computer and use it in GitHub Desktop.
Save bahamat/e9cca22830b2a3fdbb3a1a0215dec672 to your computer and use it in GitHub Desktop.
Anycast Example using Quagga on SmartOS
#!/bin/bash
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at https://mozilla.org/MPL/2.0/.
# This is the SMF start method for anycast.
# Put it in /opt/custom/smf/anycast
set -o xtrace
source /lib/svc/share/smf_include.sh || true
usage() {
echo "$0 -c <configuration> {start | stop}"
}
while getopts "c:" options
do
case $options in
c ) config="${OPTARG}";;
h ) usage;;
* ) usage; exit "$SMF_EXIT_ERR_FATAL";;
esac
done
if ! [[ -f $config ]]; then
usage
exit "$SMF_EXIT_ERR_FATAL"
fi
method_start() {
while read -a line
do
ipadm create-addr -t -T static -a local="${line[0]}" "${line[1]}"
done < "${config}"
named_pid=$(pgrep -c $(svcs -H -o ctid pkgsrc/bind))
if [[ -n $named_pid ]]; then
ppriv -s A+net_privaddr "${named_pid}"
fi
}
method_stop() {
while read -a line
do
ipadm delete-addr "${line[1]}"
done < "${config}"
}
action=${*:$OPTIND:1}
case $action in
start) method_start;;
stop) method_stop;;
*) usage; exit "$SMF_EXIT_ERR_FATAL";;
esac
exit 0
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at https://mozilla.org/MPL/2.0/.
# This is the config file for the SMF anycast service.
# The format is as follows:
#
# address/prefix-length addr-obj
#
# This will be fed directly into ipadm, and there's no sanity
# checking. Patches welcome!
1.1.1.1/32 lo0/dns1
8.8.8.8/32 lo0/dns8
<?xml version="1.0"?>
<!DOCTYPE service_bundle SYSTEM "/usr/share/lib/xml/dtd/service_bundle.dtd.1">
<!-- This Source Code Form is subject to the terms of the Mozilla Public
- License, v. 2.0. If a copy of the MPL was not distributed with this
- file, You can obtain one at https://mozilla.org/MPL/2.0/. -->
<!--
Created by Manifold
-->
<service_bundle type="manifest" name="anycast">
<service name="network/anycast" type="service" version="1.1">
<dependency name="network" grouping="require_all" restart_on="error" type="service">
<service_fmri value="svc:/milestone/network:default"/>
</dependency>
<dependency name="filesystem" grouping="require_all" restart_on="error" type="service">
<service_fmri value="svc:/system/filesystem/local"/>
</dependency>
<dependency name="bind" grouping="require_all" restart_on="restart" type="service">
<service_fmri value="svc:/pkgsrc/bind:default"/>
</dependency>
<dependency name="ospf" grouping="require_any" restart_on="restart" type="service">
<service_fmri value="svc:/pkgsrc/quagga:ospf"/>
</dependency>
<dependency name="ospf6" grouping="require_any" restart_on="restart" type="service">
<service_fmri value="svc:/pkgsrc/quagga:ospf6"/>
</dependency>
<dependency name='config-files' grouping='require_all' restart_on='refresh' type='path'>
<service_fmri value='file://localhost/opt/custom/smf/anycast.conf' />
</dependency>
<instance name="default" enabled="true">
<method_context>
</method_context>
<exec_method type="method" name="start" exec="/opt/custom/smf/anycast -c %{config_file} start" timeout_seconds="60"/>
<exec_method type="method" name="stop" exec="/opt/custom/smf/anycast -c %{config_file} stop" timeout_seconds="60"/>
<property_group name="startd" type="framework">
<propval name="duration" type="astring" value="transient"/>
<propval name="ignore_error" type="astring" value="core,signal"/>
</property_group>
<property_group name="application" type="application">
<propval name="config_file" type="astring" value="/opt/custom/smf/anycast.conf"/>
</property_group>
</instance>
<stability value="Evolving"/>
<template>
<common_name>
<loctext xml:lang="C">
Anycast
</loctext>
</common_name>
</template>
</service>
</service_bundle>
! This Source Code Form is subject to the terms of the Mozilla Public
! License, v. 2.0. If a copy of the MPL was not distributed with this
! file, You can obtain one at https://mozilla.org/MPL/2.0/.
!
<% @active.each do |int| %>
interface <%= int %>
ipv6 ospf6 priority 0
!
<% end %>
<% @passive.each do |int| %>
interface <%= int %>
ipv6 ospf6 passive
!
<% end unless @passive.nil? %>
router ospf6
router-id <%= @ip %>
<% @active.each do |int| %>
interface <%= int %> area <%= @area %>
<% end %>
<% @passive.each do |int| %>
interface <%= int %> area <%= @area %>
<% end unless @passive.nil? %>
<% @prefixes.each do |prefix| %>
area <%= @area %> range <%= prefix %>
<% end unless @prefixes.nil? %>
!
line vty
! This Source Code Form is subject to the terms of the Mozilla Public
! License, v. 2.0. If a copy of the MPL was not distributed with this
! file, You can obtain one at https://mozilla.org/MPL/2.0/.
!
<% @active.each do |int| %>
interface <%= int %>
ip ospf priority 0
!
<% end %>
router ospf
ospf router-id <%= @ip %>
log-adjacency-changes
<% @passive.each do |int| %>
passive-interface <%= int %>
<% end unless @passive.nil? %>
<% @prefixes.each do |prefix| %>
network <%= prefix %> area <%= @area %>
<% end unless @prefixes.nil? %>
redistribute kernel
!
line vty
! This Source Code Form is subject to the terms of the Mozilla Public
! License, v. 2.0. If a copy of the MPL was not distributed with this
! file, You can obtain one at https://mozilla.org/MPL/2.0/.
!
ip forwarding
!
line vty
!
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment