Gentoo Archives: gentoo-user-de

From: Helge Kaltenbach <helge@×××××××.net>
To: gentoo-user-de@l.g.o
Subject: Re: [gentoo-user-de] ERROR: "net.eth0" does not have a start function.
Date: Tue, 20 Sep 2005 16:53:50
Message-Id: 43303EB4.6050109@saphear.net
In Reply to: Re: [gentoo-user-de] ERROR: "net.eth0" does not have a start function. by Felix Schuster
1 Felix Schuster wrote:
2
3 >On Tue, 2005-09-20 at 08:48 +0200, Helge Kaltenbach wrote:
4 >
5 >
6 >>Helge Kaltenbach wrote:
7 >>
8 >>
9 >
10 >
11 >
12 >>Wäre sehr verbunden, wenn mir mal jemand diese zwei Scripte mailen
13 >>könnte. Möglichst aktuell, falls dort auch Änderungen vorgenommen wurden....
14 >>
15 >>
16 >
17 >s. Anhang
18 >net.eth0 ist ein symb. Link auf net.lo
19 >Felix
20 >
21 >
22 >
23 >------------------------------------------------------------------------
24 >
25 >#!/sbin/runscript
26 ># Copyright (c) 2004-2005 Gentoo Foundation
27 ># Distributed under the terms of the GNU General Public License v2
28 ># $Header$
29 >
30 ># Contributed by Roy Marples (uberlord@g.o)
31 ># Many thanks to Aron Griffis (agriffis@g.o)
32 ># for help, ideas and patches
33 >
34 >#NB: Config is in /etc/conf.d/net
35 >
36 >if [[ -n ${NET_DEBUG} ]]; then
37 > set -x
38 > devnull=/dev/stderr
39 >else
40 > devnull=/dev/null
41 >fi
42 >
43 ># For pcmcia users. note that pcmcia must be added to the same
44 ># runlevel as the net.* script that needs it.
45 >depend() {
46 > use coldplug hotplug pcmcia usb isdn4linux wlan
47 >
48 > # Load any custom depend functions for the given interface
49 > # For example, br0 may need eth0 and eth1
50 > local iface=${myservice##*.}
51 > [[ $( type -t depend_${iface} ) == "function" ]] && depend_${iface}
52 >}
53 >
54 ># Define where our modules are
55 >MODULES_DIR=/lib/rcscripts/net.modules.d
56 >
57 ># Load some functions shared between ourselves and our dhcp helpers
58 >source ${MODULES_DIR}/helpers.d/functions
59 >
60 ># Make some wrappers to fudge after/before/need/use depend flags.
61 ># These are callbacks so mods[i] will be set.
62 >after() {
63 > local x="$*"
64 > [[ $# -gt 1 ]] && x=$( echo -e "${x// /\n}" | sort | xargs )
65 > eval "${MODULE}_after() { echo \"$x\"; }"
66 >}
67 >before() {
68 > local x="$*"
69 > [[ $# -gt 1 ]] && x=$( echo -e "${x// /\n}" | sort | xargs )
70 > eval "${MODULE}_before() { echo \"$x\"; }"
71 >}
72 >need() {
73 > local x="$*"
74 > [[ $# -gt 1 ]] && x=$( echo -e "${x// /\n}" | sort | xargs )
75 > eval "${MODULE}_need() { echo \"$x\"; }"
76 >}
77 >installed() {
78 > local x="$*"
79 > [[ $# -gt 1 ]] && x=$( echo -e "${x// /\n}" | sort | xargs )
80 > # We deliberately misspell this as _installed will probably be used
81 > # at some point
82 > eval "${MODULE}_instlled() { echo \"$x\"; }"
83 >}
84 >
85 >sort() {
86 > LC_ALL=C /bin/sort "$@"
87 >}
88 >
89 ># void module_class_wrap(char *module, char *provides)
90 ># Setup class wrappers: interface_up -> iproute2_up, for example
91 >module_class_wrap() {
92 > local module=${1} provides=${2} x
93 >
94 > # Don't wrap functions if another module already has
95 > [[ $( type -t ${provides}_provides ) == function ]] && return
96 >
97 > for x in $( typeset -f | grep -o ^${module}_'[^ ]*' ); do
98 > eval "${provides}${x#${module}}() { ${x} \"\$@\"; }"
99 > done
100 >}
101 >
102 ># bool module_load_minimum(char *module)
103 >#
104 ># Does the minimum checking on a module - even when forcing
105 >module_load_minimum() {
106 > local f=${1} MODULE=${1##*/}
107 >
108 > if [[ ! -f ${f} ]]; then
109 > eerror "${f} does not exist"
110 > return 1
111 > fi
112 >
113 > if ! source ${f} ; then
114 > eerror "${MODULE} failed a sanity check"
115 > return 1
116 > fi
117 >
118 > for f in check_installed provides check_depends depend; do
119 > [[ $( type -t ${MODULE}_${f} ) == function ]] && continue
120 > eerror "${MODULE} does not support the required function ${f}"
121 > return 1
122 > done
123 >
124 > # Wrap our before/after/need/use functions
125 > ${MODULE}_depend
126 >
127 > return 0
128 >}
129 >
130 ># bool modules_load_auto()
131 >#
132 ># Load and check each module for sanity
133 ># If the module is not installed, the functions are to be removed
134 >modules_load_auto() {
135 > local e f i j beforefuncs afterfuncs diffs unload
136 >
137 > # Populate the MODULES array
138 > MODULES=( $( find ${MODULES_DIR}/ -maxdepth 1 -type f ! -name ".*" | sort ) )
139 >
140 > # Each of these sources into the global namespace, so it's
141 > # important that module functions and variables are prefixed with
142 > # the module name, for example iproute2_
143 >
144 > beforefuncs="$( typeset -F )"
145 > j=${#MODULES[@]}
146 > loaded_interface=false
147 > for (( i=0; i<j; i++ )); do
148 >
149 > unload=false
150 > module_load_minimum ${MODULES[i]} || unload=true
151 > MODULES[i]=${MODULES[i]##*/}
152 >
153 > ! ${unload} && ${MODULES[i]}_check_installed false || unload=true
154 >
155 > if [[ ${MODULES[i]} == interface ]]; then
156 > eerror "interface is a reserved name - cannot load a module called interface"
157 > return 1
158 > fi
159 >
160 > afterfuncs="$( typeset -F )"
161 > if ${unload} ; then
162 > unset MODULES[i]
163 > unsetfuncs="${unsetfuncs} $( diff -U0 <( echo "${beforefuncs}" ) <( echo "${afterfuncs}" ) 2>/dev/null \
164 > | awk 'BEGIN { ORS = " "; } /+declare -f/ { print $3; }' )"
165 > fi
166 > beforefuncs="${afterfuncs}"
167 >
168 > done
169 > MODULES=( "${MODULES[@]}" )
170 >
171 > return 0
172 >}
173 >
174 >
175 ># bool modules_check_installed(void)
176 >#
177 ># Ensure that all modules have the required modules loaded
178 ># This enables us to remove modules from the MODULES array
179 ># Whilst other modules can still explicitly call them
180 ># One example of this is essidnet which configures network
181 ># settings for the specific ESSID connected to as the user
182 ># may be using a daemon to configure wireless instead of our
183 ># iwconfig module
184 >modules_check_installed() {
185 > local i j missingdeps nmods=${#MODULES[@]}
186 >
187 > for (( i=0; i<nmods; i++ )); do
188 > [[ $( type -t ${MODULES[i]}_instlled ) != function ]] && continue
189 > for j in $( ${MODULES[i]}_instlled ); do
190 > missingdeps=true
191 > if [[ $( type -t ${j}_check_installed ) == function ]]; then
192 > ${j}_check_installed && missingdeps=false
193 > fi
194 > ${missingdeps} && unset MODULES[i] && unset PROVIDES[i] && break
195 > done
196 > done
197 >
198 > MODULES=( "${MODULES[@]}" )
199 > PROVIDES=( "${PROVIDES[@]}" )
200 >}
201 >
202 ># bool modules_check_user(void)
203 >modules_check_user() {
204 > local -a umods
205 > local i j k l npref nmods=${#MODULES[@]}
206 >
207 > # Has the interface got any specific modules?
208 > eval umods=( \"\$\{modules_${iface}\[@\]\}\" )
209 >
210 > # Global setting follows interface-specific setting
211 > umods=( "${umods[@]}" "${modules[@]}" )
212 >
213 > # Add our preferred modules
214 > npref=3
215 > umods=( "${umods[@]}" "ifconfig" "dhcpcd" "iwconfig" )
216 >
217 > # First we strip any modules that conflict from user settings
218 > # So if the user specifies pump then we don't use dhcpcd
219 > for (( i=0; i<${#umods[@]}; i++ )); do
220 > # Some users will inevitably put "dhcp" in their modules
221 > # list. To keep users from screwing up their system this
222 > # way, ignore this setting so that the default dhcp
223 > # module will be used.
224 > [[ ${umods[i]} == dhcp ]] && continue
225 >
226 > # We remove any modules we explicitly don't want
227 > if [[ ${umods[i]} == !* ]]; then
228 > for (( j=0; j<nmods; j++ )); do
229 > [[ -z ${MODULES[j]} ]] && continue
230 > if [[ ${umods[i]:1} == ${MODULES[j]} || ${umods[i]:1} == ${PROVIDES[j]} ]]; then
231 > # We may need to setup a class wrapper for it even though
232 > # we don't use it directly
233 > ${MODULES[j]}_check_installed && module_class_wrap ${MODULES[j]}
234 > unset MODULES[j]
235 > unset PROVIDES[j]
236 > break
237 > fi
238 > done
239 > continue
240 > fi
241 >
242 > if [[ $( type -t ${umods[i]}_provides ) != function ]]; then
243 > # If the module is one of our preferred modules, then
244 > # ignore this error; whatever is available will be
245 > # used instead.
246 > (( i < ${#umods[@]} - npref )) || continue
247 > eerror "${umods[i]} is not a valid module (missing provides)"
248 > return 1
249 > fi
250 >
251 > # Ensure that the user specified module has its package installed
252 > if (( i < ${#umods[@]} - npref )); then
253 > # $1==true causes check_installed to report its own errors
254 > ${umods[i]}_check_installed true || return 1
255 > else
256 > # If this happens on a preferred modules, ignore it;
257 > # whatever is available will be used instead.
258 > ${umods[i]}_check_installed false || continue
259 > fi
260 >
261 > mod=$( ${umods[i]}_provides )
262 > for (( j=0; j<nmods; j++ )); do
263 > [[ -z ${MODULES[j]} ]] && continue
264 > if [[ ${PROVIDES[j]} == ${mod} && ${umods[i]} != ${MODULES[j]} ]]; then
265 > # We don't have a match - now ensure that we still provide an alternative.
266 > # This is to handle our preferred modules.
267 > for (( l=0; l<nmods; l++ )); do
268 > [[ ${l} -eq ${j} || -z ${MODULES[l]} ]] && continue
269 > if [[ ${PROVIDES[l]} == ${mod} ]]; then
270 > unset MODULES[j]
271 > unset PROVIDES[j]
272 > break
273 > fi
274 > done
275 > fi
276 > done
277 > done
278 >
279 > # Then we strip conflicting modules.
280 > # We only need to do this for 3rd party modules that conflict with
281 > # our own modules and the preferred list AND the user modules
282 > # list doesn't specify a preference.
283 > for (( i=0; i<nmods-1; i++ )); do
284 > [[ -z ${MODULES[i]} ]] && continue
285 > for (( j=i+1; j<nmods; j++)); do
286 > [[ -z ${MODULES[j]} ]] && continue
287 > [[ ${PROVIDES[i]} == ${PROVIDES[j]} ]] && unset MODULES[j] && unset PROVIDES[j]
288 > done
289 > done
290 >
291 > MODULES=( "${MODULES[@]}" )
292 > PROVIDES=( "${PROVIDES[@]}" )
293 > return 0
294 >}
295 >
296 ># void modules_sort(void)
297 >
298 >modules_sort() {
299 > local -a modnums sort_history modafter modbefore
300 > local i j k p changed_something nmods=${#MODULES[@]}
301 >
302 > # Sort our modules
303 > # We do this by assigning numbers to each module
304 > # We also assign modbefore and modafter so we don't
305 > # shell out as much because it's expensive on CPU.
306 > modnums=()
307 > for (( i=0; i<nmods; i++ )); do
308 > modnums[i]=${i}
309 > [[ $( type -t ${MODULES[i]}_after ) == function ]] && modafter[i]=$( ${MODULES[i]}_after )
310 > [[ $( type -t ${MODULES[i]}_before ) == function ]] && modbefore[i]=$( ${MODULES[i]}_before )
311 > done
312 >
313 > # Then we swap numbers based on and after/before flags
314 > # until we don't swap anymore. The sort_history array prevents
315 > # the possibility of an infinite loop
316 > sort_history[0]="${modnums[*]}"
317 > for (( k=1; 1; k++ )); do
318 > changed_something=false
319 > for (( i=0; i<nmods; i++ )); do
320 > for p in ${modafter[i]}; do
321 > for (( j=0; j<nmods; j++ )); do
322 > [[ ${p} != ${MODULES[j]} && ${p} != ${PROVIDES[j]} ]] && continue
323 > if [[ ${modnums[i]} -lt ${modnums[j]} ]]; then
324 > tmp=${modnums[i]}
325 > modnums[i]=${modnums[j]}
326 > modnums[j]=${tmp}
327 > changed_something=true
328 > fi
329 > done
330 > done
331 > for p in ${modbefore[i]}; do
332 > for (( j=0; j<nmods; j++ )); do
333 > [[ ${p} != ${MODULES[j]} && ${p} != ${PROVIDES[j]} ]] && continue
334 > if [[ ${modnums[i]} -gt ${modnums[j]} ]]; then
335 > tmp=${modnums[i]}
336 > modnums[i]=${modnums[j]}
337 > modnums[j]=${tmp}
338 > changed_something=true
339 > fi
340 > done
341 > done
342 > done
343 > ${changed_something} || break
344 >
345 > # Make sure we aren't repeating a previous state
346 > # First time through, k=1, k/2=0
347 > sort_history[k]="${modnums[*]}"
348 > if [[ ${sort_history[k]} == ${sort_history[k/2]} ]]; then
349 > eerror "Detected an infinite loop sorting modules; blundering ahead"
350 > break
351 > fi
352 > done
353 >
354 > # Finally we sort our modules in number order
355 > um=""
356 > for (( i=0; i<nmods; i++ )); do
357 > um="${um}${modnums[i]} ${MODULES[i]} ${PROVIDES[i]}\n"
358 > done
359 >
360 > p=( $( echo -e "${um}" | sort -n | awk '{print $2,$3}' ) )
361 > MODULES=()
362 > PROVIDES=()
363 > j=0
364 > for (( i=0; i<${#p[@]}; i+=2 )); do
365 > MODULES[j]=${p[i]}
366 > PROVIDES[j]=${p[i+1]}
367 > (( j++ ))
368 > done
369 >}
370 >
371 ># bool modules_check_depends(bool showprovides)
372 >modules_check_depends() {
373 > local showprovides=${1:-false} nmods=${#MODULES[@]} i j needmod
374 > local missingdeps p interface=false
375 >
376 > for (( i=0; i<nmods; i++ )); do
377 > if [[ $( type -t ${MODULES[i]}_need ) == function ]]; then
378 > for needmod in $( ${MODULES[i]}_need ); do
379 > missingdeps=true
380 > for (( j=0; j<nmods; j++ )); do
381 > if [[ ${needmod} == ${MODULES[j]} || ${needmod} == ${PROVIDES[j]} ]]; then
382 > missingdeps=false
383 > break
384 > fi
385 > done
386 > if ${missingdeps} ; then
387 > eerror "${MODULES[i]} needs ${needmod} (dependency failure)"
388 > return 1
389 > fi
390 > done
391 > fi
392 >
393 > ${MODULES[i]}_check_depends || return 1
394 > [[ ${PROVIDES[i]} == interface ]] && interface=true
395 >
396 > if ${showprovides} ; then
397 > [[ ${PROVIDES[i]} != ${MODULES[i]} ]] && veinfo "${MODULES[i]} provides ${PROVIDES[i]}"
398 > fi
399 > done
400 >
401 > if ! ${interface} ; then
402 > eerror "no interface module has been loaded"
403 > return 1
404 > fi
405 >
406 > return 0
407 >}
408 >
409 ># bool modules_load(char *iface, bool starting)
410 >#
411 ># Loads the defined handler and modules for the interface
412 ># Returns 0 on success, otherwise 1
413 >modules_load() {
414 > local iface=${1} starting=${2:-true} mod p=false i j unsetfuncs
415 > local -a x
416 > local RC_INDENTATION=${RC_INDENTATION} # so it will reset after function
417 > local -a PROVIDES
418 >
419 > if [[ ${iface} == lo ]]; then
420 > # We force lo to only use these modules for a major speed boost
421 > modules_force=( "iproute2" "ifconfig" )
422 > else
423 > eval x=( \"\$\{modules_force_${iface}\[@\]\}\" )
424 > [[ -n ${x} ]] && modules_force=( "${x[@]}" )
425 > if [[ -n ${modules_force} ]]; then
426 > ewarn "WARNING: You are forcing modules!"
427 > ewarn "Do not complain or file bugs if things start breaking"
428 > report=true
429 > fi
430 > veinfo "Loading networking modules for ${iface}"
431 > fi
432 > eindent
433 >
434 > if [[ -z ${modules_force} ]]; then
435 > modules_load_auto || return 1
436 > else
437 > j=${#modules_force[@]}
438 > for (( i=0; i<j; i++ )); do
439 > module_load_minimum "${MODULES_DIR}/${modules_force[i]}" || return 1
440 > ${modules_force[i]}_check_installed || unset modules_force[i]
441 > done
442 > MODULES=( "${modules_force[@]}" )
443 > fi
444 >
445 > # We now buffer the _provides functions for a big speed boost
446 > j=${#MODULES[@]}
447 > for (( i=0; i<j; i++ )); do
448 > PROVIDES[i]=$( ${MODULES[i]}_provides )
449 > done
450 >
451 > if [[ -z ${modules_force[@]} ]]; then
452 > if ${starting}; then
453 > modules_check_user || return 1
454 > fi
455 >
456 > # We unset unloaded module functions here as so we can error
457 > # with a message informing the user to emerge the correct
458 > # package if it's in their modules
459 > [[ -n ${unsetfuncs} ]] && unset ${unsetfuncs}
460 >
461 > modules_sort
462 > fi
463 >
464 > # Setup class wrappers: interface_up -> iproute2_up, for example
465 > j=${#MODULES[@]}
466 > for (( i=0; i<j; i++ )); do
467 > module_class_wrap ${MODULES[i]} ${PROVIDES[i]}
468 > done
469 >
470 > modules_check_installed || return 1
471 >
472 > [[ ${iface} != lo ]] && veinfo "modules: ${MODULES[@]}"
473 > eindent
474 >
475 > [[ ${iface} != lo && ${starting} == true ]] && p=true
476 > modules_check_depends ${p} || return 1
477 > return 0
478 >}
479 >
480 ># bool iface_start(char *interface)
481 >#
482 ># iface_start is called from start. It's expected to start the base
483 ># interface (for example "eth0"), aliases (for example "eth0:1") and to start
484 ># VLAN interfaces (for example eth0.0, eth0.1). VLAN setup is accomplished by
485 ># calling itself recursively.
486 >iface_start() {
487 > local iface=${1} mod config_counter=-1 x warn=false config_worked=false
488 > local RC_INDENTATION=${RC_INDENTATION} # so it will reset after function
489 > local -a config fallback fallback_route conf
490 > local ifvar=$( interface_variable ${iface} )
491 >
492 > # pre Start any modules with
493 > for mod in ${MODULES[@]}; do
494 > if [[ $( type -t ${mod}_pre_start ) == function ]]; then
495 > ${mod}_pre_start ${iface} || { eend 1; return 1; }
496 > fi
497 > done
498 >
499 > # New style config - one variable fits all
500 > eval config=( \"\$\{config_${ifvar}\[@\]\}\" )
501 > eval fallback=( \"\$\{fallback_${ifvar}\[@\]\}\" )
502 > eval fallback_route=( \"\$\{fallback_route_${ifvar}\[@\]\}\" )
503 >
504 > # We must support old configs
505 > if [[ -z ${config} ]]; then
506 > interface_get_old_config ${iface} || return 1
507 > fi
508 >
509 > # Handle "noop" correctly
510 > if [[ ${config[0]} == "noop" ]]; then
511 > if interface_is_up ${iface} true ; then
512 > einfo "Keeping current configuration for ${iface}"
513 > eend 0
514 > return 0
515 > fi
516 >
517 > # Remove noop from the config var
518 > config=( "${config[@]:1}" )
519 > fi
520 >
521 > # Provide a default of DHCP if no configuration is set
522 > if [[ -z ${config} ]]; then
523 > if [[ $( type -t dhcp_start ) == function ]]; then
524 > config=( "dhcp" )
525 > warn=true
526 > else
527 > eerror "Cannot default to dhcp as there is no dhcp module loaded"
528 > eerror "No configuration for ${iface}"
529 > return 1
530 > fi
531 > fi
532 >
533 > einfo "Bringing up ${iface}"
534 > eindent
535 > for (( config_counter=0; config_counter<${#config[@]}; config_counter++ )); do
536 > # Handle null and noop correctly
537 > if [[ ${config[config_counter]} == "null" \
538 > || ${config[config_counter]} == "noop" ]]; then
539 > eend 0
540 > config_worked=true
541 > continue
542 > fi
543 >
544 > if ${warn}; then
545 > ewarn "Configuration not set for ${iface} - assuming dhcp"
546 > warn=false
547 > fi
548 >
549 > # We convert it to an array - this has the added
550 > # bonus of trimming spaces!
551 > conf=( ${config[config_counter]} )
552 > einfo "${conf[0]}"
553 >
554 > # Do we have a function for our config?
555 > if [[ $( type -t ${conf[0]}_start ) == function ]]; then
556 > # Check that the module is valid
557 > x=false
558 > for mod in ${MODULES[@]}; do
559 > if [[ $( ${mod}_provides ) == ${conf[0]} ]]; then
560 > x=true
561 > break
562 > fi
563 > done
564 >
565 > if ! ${x}; then
566 > [[ $( type -t ${conf[0]}_check_installed == function ) ]] && ${conf[0]}_check_installed true
567 > eerror "No loaded modules provide \"${conf[0]}\" (${conf[0]}_start)"
568 > else
569 > eindent
570 > ${conf[0]}_start ${iface} ; x=$?
571 > eoutdent
572 > [[ ${x} == 0 ]] && config_worked=true && continue
573 > fi
574 > # We need to test to see if it's an IP address or a function
575 > # We do this by testing if the 1st character is a digit
576 > elif [[ ${conf[0]:0:1} == [[:digit:]] || ${conf[0]} == *:* ]]; then
577 > x=0
578 ># if [[ $(type -t address_exists ) == function ]]; then
579 ># if address_exists ${iface} ${conf[0]} ; then
580 ># eerror "${conf[0]%%/*} already taken on ${iface}"
581 ># x=1
582 ># fi
583 ># fi
584 > [[ ${x} == 0 ]] && interface_add_address ${iface} ${conf[@]} ; x=$?
585 > eend ${x} && config_worked=true && continue
586 > else
587 > eerror "No loaded modules provide \"${conf[0]}\" (${conf[0]}_start)"
588 > fi
589 >
590 > if [[ -n ${fallback[config_counter]} ]]; then
591 > einfo "Trying fallback configuration"
592 > config[config_counter]=${fallback[config_counter]}
593 > fallback[config_counter]=''
594 >
595 > # Do we have a fallback route?
596 > if [[ -n ${fallback_route[config_counter]} ]]; then
597 > eval "routes_${ifvar}=( "\"\$\{fallback_route\[${config_counter}\]\[@\]\}\"" )"
598 > fallback_route[config_counter]=''
599 > fi
600 >
601 > (( config_counter-- )) # since the loop will increment it
602 > continue
603 > fi
604 > done
605 > eoutdent
606 >
607 > # We return failure if no configuration parameters worked
608 > ${config_worked} || return 1
609 >
610 > # Start any modules with _post_start
611 > for mod in ${MODULES[@]}; do
612 > if [[ function == $( type -t ${mod}_post_start ) ]]; then
613 > ${mod}_post_start ${iface} || return 1
614 > fi
615 > done
616 >
617 > return 0
618 >}
619 >
620 ># bool iface_stop(char *interface)
621 >#
622 ># iface_stop: bring down an interface. Don't trust information in
623 ># /etc/conf.d/net since the configuration might have changed since
624 ># iface_start ran. Instead query for current configuration and bring
625 ># down the interface.
626 >#
627 ># However, we are currently reliant on handler and modules specified
628 ># in /etc/conf.d/net
629 >iface_stop() {
630 > local iface=${1} i aliases need_begin=false mod
631 > local RC_INDENTATION=${RC_INDENTATION} # so it will reset after function
632 >
633 > # pre Stop any modules
634 > for mod in ${MODULES[@]}; do
635 > [[ $( type -t ${mod}_pre_stop ) == function ]] && ${mod}_pre_stop ${iface}
636 > done
637 >
638 > einfo "Bringing down ${iface}"
639 > eindent
640 >
641 > # Collect list of aliases for this interface.
642 > # List will be in reverse order.
643 > aliases=$( interface_get_aliases_rev ${iface} )
644 >
645 > # Stop aliases before primary interface.
646 > # Note this must be done in reverse order, since ifconfig eth0:1
647 > # will remove eth0:2, etc. It might be sufficient to simply remove
648 > # the base interface but we're being safe here.
649 > for i in ${aliases} ${iface}; do
650 > # Stop all our modules
651 > for mod in ${MODULES[@]}; do
652 > [[ $( type -t ${mod}_stop ) == function ]] && ${mod}_stop ${i}
653 > done
654 >
655 > # A module may have removed the interface
656 > interface_exists ${iface} || { eend 0; continue; }
657 >
658 > # Delete all the addresses for this alias
659 > interface_del_addresses ${i}
660 >
661 > # Do final shut down of this alias
662 > ebegin "Shutting down ${i}"
663 > interface_iface_stop ${i}
664 > eend $?
665 > done
666 >
667 > # post Stop any modules
668 > for mod in ${MODULES[@]}; do
669 > # We have already taken down the interface, so no need to error
670 > [[ $( type -t ${mod}_post_stop ) == function ]] && ${mod}_post_stop ${iface}
671 > done
672 >
673 > return 0
674 >}
675 >
676 ># bool run_start(char *iface)
677 >#
678 ># Brings up ${IFACE}. Calls preup, iface_start, then postup.
679 ># Returns 0 (success) unless preup or iface_start returns 1 (failure).
680 ># Ignores the return value from postup.
681 ># We cannot check that the device exists ourselves as modules like
682 ># tuntap make create it.
683 >run_start() {
684 > local iface=${1} ifvar x
685 >
686 > if [[ ${iface} == lo ]]; then
687 > ebegin "Bringing up ${iface}"
688 > interface_loopback_create
689 > eend $?
690 > return $?
691 > fi
692 >
693 > # We may not have a loaded module for ${iface}
694 > # Some users may have "alias natsemi eth0" in /etc/modules.d/foo
695 > # so we can work with this
696 > # However, if they do the same with eth1 and try to start it
697 > # but eth0 has not been loaded then the module gets loaded as
698 > # eth0.
699 > # Not much we can do about this :(
700 > # Also, we cannot error here as some modules - such as bridge
701 > # create interfaces
702 > if ! interface_exists ${iface} ; then
703 > /sbin/modprobe ${iface} &>/dev/null
704 > fi
705 >
706 > # Setup variables for pre/post to use
707 > ifvar=$( interface_variable ${iface} )
708 > local IFACE=${iface} IFVAR=${ifvar}
709 >
710 > # Call user-defined preup function if it exists
711 > if [[ $( type -t preup ) == function ]]; then
712 > einfo "Running preup function"
713 > eindent
714 > preup ${iface} ; x=$?
715 > eoutdent
716 > if [[ ${x} != 0 ]]; then
717 > eerror "preup ${iface} failed"
718 > return 1
719 > fi
720 > fi
721 >
722 > # Don't let preup modify us
723 > iface=${1}
724 > local IFACE=${iface} IFVAR=${ifvar} config
725 >
726 > # If config is set to noop and the interface is up with an address
727 > # then we don't start it
728 > eval config=( \"\$\{config_${ifvar}\[@\]\}\" )
729 > if [[ ${config[0]} == "noop" ]] && interface_is_up ${iface} true ; then
730 > einfo "Keeping current configuration for ${iface}"
731 > eend 0
732 > else
733 > # Remove noop from the config var
734 > [[ ${config[0]} == "noop" ]] && eval "config_${ifvar}=( "\"\$\{config\[@\]:1\}\"" )"
735 >
736 > # There may be existing ip address info - so we strip it
737 > interface_del_addresses ${iface}
738 >
739 > # Start the interface
740 > if ! iface_start ${iface} ; then
741 > interface_exists ${iface} && interface_down ${iface}
742 > eend 1
743 > return 1
744 > fi
745 > fi
746 >
747 > # Call user-defined postup function if it exists
748 > if [[ $( type -t postup ) == function ]]; then
749 > einfo "Running postup function"
750 > eindent
751 > postup ${iface}
752 > eoutdent
753 > fi
754 >
755 > return 0
756 >}
757 >
758 ># bool run_stop(char *iface) {
759 >#
760 ># Brings down ${iface}. If predown call returns non-zero, then
761 ># stop returns non-zero to indicate failure bringing down device.
762 ># In all other cases stop returns 0 to indicate success.
763 >run_stop() {
764 > local iface=${1} ifvar x
765 >
766 > # Don't run any special shutdown functions for lo
767 > if [[ ${iface} == lo ]]; then
768 > ebegin "Shutting down ${iface}"
769 > interface_iface_stop ${iface}
770 > eend $?
771 > return 0
772 > fi
773 >
774 > # Setup variables for pre/post to use
775 > ifvar=$( interface_variable ${iface} )
776 > local IFACE=${iface} IFVAR=${ifvar}
777 >
778 > # Call user-defined predown function if it exists
779 > if [[ $( type -t predown ) == function ]]; then
780 > einfo "Running predown function"
781 > eindent
782 > predown ${iface} ; x=$?
783 > eoutdent
784 > if [[ ${x} != 0 ]]; then
785 > eend 1 "predown ${iface} failed"
786 > return 1
787 > fi
788 > elif is_net_fs /; then
789 > eerror "root filesystem is network mounted -- can't stop ${iface}"
790 > return 1
791 > fi
792 >
793 > # Don't let predown modify us
794 > iface=${1}
795 > local IFACE=${iface} IFVAR=${ifvar}
796 >
797 > iface_stop ${iface} || return 1 # always succeeds, btw
798 >
799 > # Call user-defined postdown function if it exists
800 > if [[ $( type -t postdown ) == function ]]; then
801 > einfo "Running postdown function"
802 > eindent
803 > postdown ${iface}
804 > eoutdent
805 > fi
806 >
807 > return 0
808 >}
809 >
810 ># bool run(char *iface, char *cmd)
811 >#
812 ># Main start/stop entry point
813 ># We load modules here and remove any functions that they
814 ># added as we may be called inside the same shell scope for another interface
815 >run() {
816 > local iface=${1} cmd=${2} r=1 RC_INDENTATION=${RC_INDENTATION} # so it will reset after function
817 > local before starting=true
818 > local -a MODULES mods
819 >
820 > # We need to override the exit function as runscript.sh now checks
821 > # for it. We need it so we can mark the service as inactive ourselves.
822 > unset -f exit
823 >
824 > eindent
825 >
826 > unset_functions=${unset_functions:-false}
827 > ${unset_functions} && before="$( typeset -F )"
828 > [[ ${cmd} == "stop" ]] && starting=false
829 > if modules_load ${iface} ${starting} ; then
830 > if [[ ${cmd} == "stop" ]]; then
831 > # Reverse the module list for stopping
832 > mods=( "${MODULES[@]}" )
833 > for ((i = 0; i < ${#mods[@]}; i++)); do
834 > MODULES[i]=${mods[((${#mods[@]} - i - 1))]}
835 > done
836 >
837 > run_stop ${iface} && r=0
838 > else
839 > run_start ${iface} && r=0
840 > fi
841 > fi
842 >
843 > # We need to remove added functions before we quit as other init
844 > # scripts may be launching afterwards
845 > ${unset_functions} && \
846 > unset $( diff -U0 <( echo "${before}" ) <( echo "$( typeset -F )" ) 2>/dev/null \
847 > | awk 'BEGIN { ORS = " "; } /+declare -f/ { print $3; }' ) 2>/dev/null
848 >
849 > return ${r}
850 >}
851 >
852 ># bool start(void)
853 >#
854 ># Start entry point so that we only have one function
855 ># which localises variables and unsets functions
856 >start() {
857 > einfo "Starting ${IFACE}"
858 > run ${IFACE} start
859 > return $?
860 >}
861 >
862 ># bool stop(void)
863 >#
864 ># Stop entry point so that we only have one function
865 ># which localises variables and unsets functions
866 >stop() {
867 > einfo "Stopping ${IFACE}"
868 > run ${IFACE} stop
869 > return $?
870 >}
871 >
872 ># bool restart(void)
873 >#
874 ># Restart entry point
875 ># We do this so as we only have to remove functions when stopping
876 >restart() {
877 > local unset_functions=true
878 > service_started "${myservice}" && svc_stop
879 > unset_functions=false
880 > svc_start
881 > return $?
882 >}
883 >
884 ># vim:ts=4
885 >
886 >
887 Danke an alle, Probleme sind erstmal gelöst :)
888 --
889 gentoo-user-de@g.o mailing list

Replies

Subject Author
[gentoo-user-de] Quoting (was: ERROR: "net.eth0" does not have a start function.) Markus Rennings <news@××××××××.net>