summaryrefslogtreecommitdiffstats
path: root/src/lib/network
blob: a87510116b597d4fa688f6d73a09c3397c8e1e5e (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
#! /bin/bash

. /usr/lib/network/globals


## Check if a string represents a network interface
# $1: potential interface name
is_interface() {
    # Strip any old school alias specifier
    [[ -d "/sys/class/net/${1%%:?*}" ]]
}

## Add an interface
# $1: interface type
# $2: interface name
# $3: interface link (optional)
# $4...: additional arguments
interface_add() {
    local type="$1" name="$2" link="$3"
    shift 3
    ip link add ${link:+link "$link"} name "$name" type "$type" "$@" || return
    if [[ -x "$PROFILE_DIR/interfaces/$name" ]]; then
        source "$PROFILE_DIR/interfaces/$name"
    fi
}

## Delete an interface
# $1: interface name
interface_delete() {
    bring_interface_down "$1"
    ip link delete "$1"
}

## Check if an interface is up
# $1: interface name
interface_is_up() {
    local flags
    read flags < "/sys/class/net/${1%%:?*}/flags"
    # IFF_UP is defined as 0x1 in linux/if.h
    (( flags & 0x1 ))
}

## Activate an interface
# $1: interface name
bring_interface_up() {
    local interface=$1
    ip link set dev "$interface" up &>/dev/null
    timeout_wait "${TimeoutUp:-5}" 'interface_is_up "$interface"'
}

## Deactivate an interface
# $1: interface name
bring_interface_down() {
    local interface=$1
    ip link set dev "$interface" down &>/dev/null
    # We reuse the up timeout (down normally is faster)
    timeout_wait "${TimeoutUp:-5}" '! interface_is_up "$interface"'
}


if [[ $# -ne 2 || $1 != @(start|stop) ]]; then
    exit_error "Usage: $0 {start|stop} <profile>"
fi
ensure_root netctl
# Ensure we are not in a transient directory
cd /

# Expose the profile name
Profile=$2
load_profile "$Profile"
case $1 in
  start)
    report_notice "Starting network profile '$Profile'..."
    if is_interface "$Interface" && interface_is_up "$Interface" && \
       ! is_yes "${ForceConnect:-no}"; then
        report_error "The interface of network profile '$Profile' is already up"
        exit 1
    fi
    if ! "${Connection}_up"; then
        report_error "Failed to bring the network up for profile '$Profile'"
        exit 1
    fi
    # JP: sandbox the eval
    if ! ( eval $ExecUpPost ); then
        report_error "ExecUpPost failed for network profile '$Profile'"
        # Failing ExecUpPost will take the connection down
        "${Connection}_down"
        exit 1
    fi
    report_notice "Started network profile '$Profile'"
  ;;
  stop)
    report_notice "Stopping network profile '$Profile'..."
    # JP: sandbox the eval
    if ! ( eval $ExecDownPre ); then
        report_error "ExecDownPre failed for network profile '$Profile'"
        # Failing ExecDownPre will leave the profile active
        exit 1
    fi
    if ! "${Connection}_down"; then
        report_error "Failed to bring the network down for profile '$Profile'"
        exit 1
    fi
    if is_interface "$Interface" && interface_is_up "$Interface" && \
       ! is_yes "${ForceConnect:-no}"; then
        report_error "The interface of network profile '$Profile' did not go down"
        exit 1
    fi
    report_notice "Stopped network profile '$Profile'"
  ;;
esac


# vim: ft=sh ts=4 et sw=4: