5 # The contents of this file are subject to the terms of the
6 # Common Development and Distribution License (the "License").
7 # You may not use this file except in compliance with the License.
9 # You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10 # or http://www.opensolaris.org/os/licensing.
11 # See the License for the specific language governing permissions
12 # and limitations under the License.
14 # When distributing Covered Code, include this CDDL HEADER in each
15 # file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16 # If applicable, add the following below this CDDL HEADER, with the
17 # fields enclosed by brackets "[]" replaced with your own identifying
18 # information: Portions Copyright [yyyy] [name of copyright owner]
23 # Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
26 .
/lib
/svc
/share
/smf_include.sh
27 .
/lib
/svc
/share
/net_include.sh
30 AUTOFS_FMRI
="svc:/system/filesystem/autofs"
31 DNS_CLIENT_FMRI
="svc:/network/dns/client"
32 IPSEC_IKE_FMRI
="svc:/network/ipsec/ike"
33 IPSEC_POLICY_FMRI
="svc:/network/ipsec/policy"
34 IPFILTER_FMRI
="svc:/network/ipfilter:default"
35 LDAP_CLIENT_FMRI
="svc:/network/ldap/client"
36 LOCATION_FMRI
="svc:/network/location:default"
37 MAPID_FMRI
="svc:/network/nfs/mapid:default"
38 NIS_CLIENT_FMRI
="svc:/network/nis/client"
39 NWAM_FMRI
="svc:/network/physical:nwam"
43 DHCPINFO
=/sbin
/dhcpinfo
44 DOMAINNAME
=/usr
/bin
/domainname
46 LDAPCLIENT
=/usr
/sbin
/ldapclient
50 NWAMADM
=/usr
/sbin
/nwamadm
51 NWAMCFG
=/usr
/sbin
/nwamcfg
54 SVCADM
=/usr
/sbin
/svcadm
55 SVCCFG
=/usr
/sbin
/svccfg
56 SVCPROP
=/usr
/bin
/svcprop
60 ETC_DEFAULT_DOMAIN
=/etc
/defaultdomain
61 NIS_BIND_PATH
=/var
/yp
/binding
62 LEGACY_LOC_PATH
=/etc
/nwam
/loc
/Legacy
63 USER_LOC_PATH
=/etc
/nwam
/loc
/User
64 SCRIPT_PATH
=/etc
/svc
/volatile
/nwam
67 # echoes DHCP controlled interfaces separated by commas
69 # Don't parse the output of ifconfig(1M) because interfaces that haven't
70 # acquired a DHCP lease also have the DHCP flag set.
72 get_dhcp_interfaces
() {
74 # 1. parse netstat(1M) output for v4 interfaces in BOUND
75 # or INFORMATION state
76 # 2. make a space-separated list of interface names
78 netstat
-D -f inet |
$NAWK '
79 $2 ~ /BOUND/ { printf "%s ", $1 }
80 $2 ~ /INFORMATION/ { printf "%s ", $1 }'
84 # get_dhcpinfo <code/identifier>
86 # echoes the value received through each interface controlled by DHCP;
87 # multiple values are echoed as a space-separated list
90 # 0 => property is set
91 # 1 => property is not set
96 # Get all interfaces with DHCP control, IFS is " "
97 interfaces
=`get_dhcp_interfaces`
100 for intf
in $interfaces; do
101 val
=`$DHCPINFO -i $intf $code`
102 if [ $?
-eq 0 ]; then
103 if [ "$info" = "" ]; then
114 # set_smf_prop <fmri> <property name> <property value>
117 $SVCCFG -s $1 setprop
$2 = astring
: "$3" && return
123 # Refreshes the service.
132 # Restarts the service.
141 # Starts the service. If the service is already enabled, restarts it. If
142 # it is not enabled, temporarily enables it.
145 if service_is_enabled
$1; then
155 # Temporarily disables the service.
158 $SVCADM disable
-t $1
162 # copy_default <dir> <file>
164 # Copies <dir>/<file>.dfl to <dir>/<file>
167 $CP -p $1/$2.dfl
$1/$2
173 # Installs DNS information on /etc/resolv.conf for location
175 # Returns 0 on success, 1 on failure
179 file=/etc
/resolv.conf
181 # Write out to temporary file first
184 DNS_CONFIGSRC
=`nwam_get_loc_list_prop $loc dns-nameservice-configsrc`
185 if [ -z "$DNS_CONFIGSRC" ]; then
186 echo "missing 'dns-nameservice-configsrc' property for '$loc'"
190 for configsrc
in $DNS_CONFIGSRC; do
193 DNS_SERVERS
=`nwam_get_loc_list_prop $loc \
194 dns-nameservice-servers`
195 if [ -z "$DNS_SERVERS" ]; then
196 echo "DNS nameserver not set for '$loc'"
199 DNS_DOMAIN
=`nwam_get_loc_prop $loc \
200 dns-nameservice-domain`
201 DNS_SEARCH
=`nwam_get_loc_list_prop $loc \
202 dns-nameservice-search`
205 DNS_SEARCH
=`get_dhcpinfo DNSdmain`
206 DNS_SERVERS
=`get_dhcpinfo DNSserv`
207 # Use first search list entry as default domain
212 echo "Unrecognized DNS configsrc ${configsrc}; ignoring"
217 if [ -n "$DNS_DOMAIN" ]; then
218 echo "$DNS_DOMAIN" |
$NAWK \
219 '{ for (i = 1; i <= NF; i++) \
220 print "domain ", $i }' >> $file.$$
222 if [ -n "$DNS_SEARCH" ]; then
223 echo "$DNS_SEARCH" |
$NAWK \
224 '{ printf("search"); \
225 for (i = 1; i <= NF; i++) printf(" %s", $i); \
226 printf("\n") }' >> $file.$$
228 if [ -n "$DNS_SERVERS" ]; then
229 echo "$DNS_SERVERS" |
$NAWK \
230 '{ for (i = 1; i <= NF; i++) \
231 print "nameserver ", $i }' >> $file.$$
235 # Finally, copy our working version to the real thing
236 $MV -f $file.$$
$file
237 start_svc
$DNS_CLIENT_FMRI
245 # Installs NIS information on /var/yp/binding/ for location
247 # Returns 0 on success, 1 on failure
252 NIS_CONFIGSRC
=`nwam_get_loc_list_prop $loc nis-nameservice-configsrc`
253 if [ -z "$NIS_CONFIGSRC" ]; then
254 echo "missing 'nis-nameservice-configsrc' property for '$loc'"
258 for configsrc
in $NIS_CONFIGSRC; do
261 NIS_SERVERS
=`nwam_get_loc_list_prop $loc \
262 nis-nameservice-servers`
263 DEFAULT_DOMAIN
=`nwam_get_loc_prop $loc default-domain`
264 # user-specified default-domain always wins
265 if [ -n "$DEFAULT_DOMAIN" ]; then
266 $DOMAINNAME $DEFAULT_DOMAIN
267 $DOMAINNAME > $ETC_DEFAULT_DOMAIN
269 echo "'domainname' not set for '$loc'"
274 # Use only the first name
275 DEFAULT_DOMAIN
=`get_dhcpinfo NISdmain | \
276 $NAWK '{ print $1 }'`
277 NIS_SERVERS
=`get_dhcpinfo NISservs`
278 $DOMAINNAME $DEFAULT_DOMAIN
279 $DOMAINNAME > $ETC_DEFAULT_DOMAIN
282 echo "Unrecognized NIS configsrc ${configsrc}; ignoring"
286 # Place NIS settings in appropriate directory/file.
287 if [ ! -d "$NIS_BIND_PATH/$DEFAULT_DOMAIN" ]; then
288 $MKDIR -p $NIS_BIND_PATH/$DEFAULT_DOMAIN
290 if [ -n "$NIS_SERVERS" ]; then
291 echo "$NIS_SERVERS" |
$NAWK \
292 '{ for (i = 1; i <= NF; i++) print $i }' \
293 > $NIS_BIND_PATH/$DEFAULT_DOMAIN/ypservers
297 start_svc
$NIS_CLIENT_FMRI
305 # Installs LDAP information using ldapclient(1M) for location
307 # Returns 0 on success, 1 on failure
312 LDAP_CONFIGSRC
=`nwam_get_loc_list_prop $loc ldap-nameservice-configsrc`
313 if [ -z "$LDAP_CONFIGSRC" ]; then
314 echo "missing 'ldap-nameservice-configsrc' property for '$loc'"
318 for configsrc
in $LDAP_CONFIGSRC; do
321 LDAP_SERVERS
=`nwam_get_loc_list_prop $loc \
322 ldap-nameservice-servers`
323 DEFAULT_DOMAIN
=`nwam_get_loc_prop $loc default-domain`
324 if [ -z $LDAP_SERVERS -o -z $DEFAULT_DOMAIN ]; then
325 echo "LDAP configuration could not be set "\
329 $DOMAINNAME $DEFAULT_DOMAIN
330 $DOMAINNAME > $ETC_DEFAULT_DOMAIN
333 echo "Invalid LDAP configsrc ${configsrc}; ignoring"
337 # Use ldapclient(1M) to initialize LDAP client settings.
338 if [ -n "$DEFAULT_DOMAIN" -o -n "$LDAP_SERVERS" ]; then
339 $LDAPCLIENT init
-a domainName
=$DEFAULT_DOMAIN \
344 start_svc
$LDAP_CLIENT_FMRI
352 # Installs different nameservices for location
354 # Returns 0 on success, 1 on failure
360 # Disable nameservices temporarily while we reconfigure. Copy
361 # /etc/nsswitch.files to /etc/nsswitch.conf first so that only "files"
364 $CP -p /etc
/nsswitch.files
/etc
/nsswitch.conf
365 stop_svc
$DNS_CLIENT_FMRI
366 stop_svc
$NIS_CLIENT_FMRI
367 stop_svc
$LDAP_CLIENT_FMRI
370 # Remove /etc/defaultdomain and unset domainname(1M). If NIS
371 # and/or LDAP is configured, they will create /etc/defaultdomain
372 # and set the domainname(1M).
374 $RM -f $ETC_DEFAULT_DOMAIN
377 NAMESERVICES
=`nwam_get_loc_list_prop $loc nameservices`
378 if [ -z "$NAMESERVICES" ]; then
379 echo "missing 'nameservices' property for location '$loc'"
383 NAMESERVICES_CONFIG_FILE
=`nwam_get_loc_prop \
384 $loc nameservices-config-file`
385 if [ -z "$NAMESERVICES_CONFIG_FILE" ]; then
386 echo "missing 'nameservices-config-file' property for '$loc'"
389 $CP -p $NAMESERVICES_CONFIG_FILE /etc
/nsswitch.conf
391 for ns
in $NAMESERVICES; do
394 # no additional setup needed for files nameservice
397 do_dns
$loc ||
return 1
400 do_nis
$loc ||
return 1
403 do_ldap
$loc ||
return 1
406 echo "Unrecognized nameservices value ${ns}; ignoring"
412 # Restart other related services
414 # We explicitly restart here, as restart will only have an
415 # effect if the service is already enabled. We don't want
416 # to enable the service if it's currently disabled.
418 restart_svc
$AUTOFS_FMRI
426 # If config properties are set, update the SMF property and refresh the
427 # service. If config properties are not set, delete the SMF property and
430 # Returns 0 on success, 1 on failure
435 ike_file
=`nwam_get_loc_prop $loc ike-config-file`
436 pol_file
=`nwam_get_loc_prop $loc ipsecpolicy-config-file`
437 ipf_file
=`nwam_get_loc_prop $loc ipfilter-config-file`
438 ipf6_file
=`nwam_get_loc_prop $loc ipfilter-v6-config-file`
439 ipnat_file
=`nwam_get_loc_prop $loc ipnat-config-file`
440 ippool_file
=`nwam_get_loc_prop $loc ippool-config-file`
443 if [ -n "$ike_file" ]; then
444 set_smf_prop
$IPSEC_IKE_FMRI config
/config_file
$ike_file
445 refresh_svc
$IPSEC_IKE_FMRI
446 start_svc
$IPSEC_IKE_FMRI
448 stop_svc
$IPSEC_IKE_FMRI
452 if [ -n "$pol_file" ]; then
453 set_smf_prop
$IPSEC_POLICY_FMRI config
/config_file
$pol_file
454 refresh_svc
$IPSEC_POLICY_FMRI
455 start_svc
$IPSEC_POLICY_FMRI
457 stop_svc
$IPSEC_POLICY_FMRI
462 if [ -n "$ipf_file" ]; then
463 if [ "$ipf_file" = "/none" ]; then
464 set_smf_prop
$IPFILTER_FMRI \
465 firewall_config_default
/policy
"none"
466 elif [ "$ipf_file" = "/deny" ]; then
467 set_smf_prop
$IPFILTER_FMRI \
468 firewall_config_default
/policy
"deny"
469 elif [ "$ipf_file" = "/allow" ]; then
470 set_smf_prop
$IPFILTER_FMRI \
471 firewall_config_default
/policy
"allow"
473 # custom policy with policy file
474 set_smf_prop
$IPFILTER_FMRI \
475 firewall_config_default
/policy
"custom"
476 set_smf_prop
$IPFILTER_FMRI \
477 firewall_config_default
/custom_policy_file
$ipf_file
481 # change policy to "none", no need to clear custom_policy_file
482 set_smf_prop
$IPFILTER_FMRI firewall_config_default
/policy \
484 # IPFilter has to be refreshed to make the changes effective.
485 # Don't set $refresh_ipf as it keeps IPFilter online rather
486 # than disabled. Refresh after IPFilter is disabled below.
488 if [ -n "$ipf6_file" ]; then
489 set_smf_prop
$IPFILTER_FMRI config
/ipf6_config_file
$ipf6_file
492 if [ -n "$ipnat_file" ]; then
493 set_smf_prop
$IPFILTER_FMRI config
/ipnat_config_file
$ipnat_file
496 if [ -n "$ippool_file" ]; then
497 set_smf_prop
$IPFILTER_FMRI config
/ippool_config_file \
502 if [ "$refresh_ipf" = "true" ]; then
503 refresh_svc
$IPFILTER_FMRI
504 start_svc
$IPFILTER_FMRI
506 stop_svc
$IPFILTER_FMRI
507 refresh_svc
$IPFILTER_FMRI
514 # do_nfsv4 <location>
516 # Updates NFSv4 domain for location in SMF
518 # Returns 0 on success, 1 on failure
523 nfsv4domain
=`nwam_get_loc_prop $loc nfsv4-domain`
524 if [ $?
-eq 0 ]; then
525 set_smf_prop
$MAPID_FMRI \
526 nfs-props
/nfsmapid_domain
$nfsv4domain
527 start_svc
$MAPID_FMRI
536 # activate_loc <location>
538 # Activates the given location
540 # Returns 0 on success, 1 on failure
545 echo activating
$loc location
548 # if we fail to complete any part of the config,
549 # stop activation work and report failure.
551 do_sec
$loc && do_ns
$loc && do_nfsv4
$loc && return 0
558 # Arguments to net-loc are
559 # method ('start' or 'refresh')
562 # If nwam is not enabled, do nothing and return OK.
564 service_is_enabled
$NWAM_FMRI ||
exit $SMF_EXIT_OK
567 # In a shared-IP zone we need this service to be up, but all of the work
568 # it tries to do is irrelevant (and will actually lead to the service
569 # failing if we try to do it), so just bail out.
570 # In the global zone and exclusive-IP zones we proceed.
572 smf_configure_ip ||
exit $SMF_EXIT_OK
578 # We need to create the default (NoNet and Automatic)
579 # locations, if they don't already exist. So: first check
580 # for the existence of each, and then run the appropriate
581 # nwamcfg script(s) as needed. Restart nwamd if a location is
582 # created, as it needs to read it in.
585 $NWAMCFG list loc Automatic
>/dev
/null
2>&1
586 if [ $?
-eq 1 ]; then
587 $NWAMCFG -f /etc
/nwam
/loc
/create_loc_auto
591 $NWAMCFG list loc NoNet
>/dev
/null
2>&1
592 if [ $?
-eq 1 ]; then
593 NONETPATH
=/etc
/nwam
/loc
/NoNet
594 NONETFILES
="ipf.conf ipf6.conf"
595 for file in $NONETFILES; do
596 copy_default
$NONETPATH $file
598 $NWAMCFG -f /etc
/nwam
/loc
/create_loc_nonet
602 if [ "$LOC_CREATED" = "true" ]; then
603 refresh_svc
$NWAM_FMRI
606 # location selection/activation happens below
611 # location selection/activation happens below
615 echo "Usage: $0 start|refresh"
622 # If the Legacy location doesn't exist and the file to create the Legacy
623 # location exists, create the Legacy location. Make a copy of it as the user's
624 # intentions before upgrade. Then activate the User location if nis is
625 # involved. Because NIS affects more parts of the system (e.g. automounts) we
626 # are not willing to make NIS part of the Automatic location (i.e. enable it
627 # automatically based on external input) as we do with DHCP-driven DNS.
630 $NWAMCFG list loc Legacy
>/dev
/null
2>&1
631 if [ $?
-eq 1 -a -f "$SCRIPT_PATH/create_loc_legacy" ]; then
633 # We built the script in and pointing to /etc/svc/volatile because we
634 # may not have a writable filesystem in net-nwam. So here we move the
635 # components and rewrite the script to point at the writable filesystem.
637 $CP -r $SCRIPT_PATH/Legacy
/etc
/nwam
/loc
638 $MV $SCRIPT_PATH/create_loc_legacy
$SCRIPT_PATH/vcreate_loc_legacy
639 $SED -e's,$SCRIPT_PATH/Legacy,$LEGACY_LOC_PATH,' \
640 $SCRIPT_PATH/vcreate_loc_legacy
>$SCRIPT_PATH/create_loc_legacy
641 $RM -f $SCRIPT_PATH/vcreate_loc_legacy
642 $NWAMCFG -f $SCRIPT_PATH/create_loc_legacy
643 loc_ver
=`$SVCPROP -c -p location_upgrade/version $LOCATION_FMRI \
645 if [ $?
-eq 1 ]; then
647 # We are rewriting configuration variables from the Legacy
648 # location to the User location. Use variable ULP to keep REs
652 $SED -e's,Legacy,User,' \
653 -e's,activation-mode=system,activation-mode=manual,' \
654 -e"s,\(ipfilter-config-file=\).*/\(.*\),\1$ULP/\2," \
655 -e"s,\(ipfilter-v6-config-file=\).*/\(.*\),\1$ULP/\2," \
656 -e"s,\(ipnat-config-file=\).*/\(.*\),\1$ULP/\2," \
657 -e"s,\(ippool-config-file=\).*/\(.*\),\1$ULP/\2," \
658 -e"s,\(ike-config-file=\).*/\(.*\),\1$ULP/\2," \
659 -e"s,\(ipsecpolicy-config-file=\).*/\(.*\),\1$ULP/\2," \
660 $SCRIPT_PATH/create_loc_legacy | \
661 $SED -e's,/etc/nwam/loc/User/none,/none,' \
662 -e's,/etc/nwam/loc/User/allow,/allow,' \
663 -e's,/etc/nwam/loc/User/deny,/deny,' \
664 >$SCRIPT_PATH/create_loc_user
666 # We are creating the User location here. The User location
667 # is an appromixation of the machine configuration when the
668 # user change or upgraded to this version of NWAM. First
669 # we make sure there isn't an existing User location or any
670 # existing User location data. We then copy all the data
671 # from the Legacy location and create a location pointing at
672 # that data. Lastly we create a version property to note
673 # that we have done this.
675 $NWAMCFG destroy loc User
2>/dev
/null
676 $RM -rf $USER_LOC_PATH
677 $CP -r $LEGACY_LOC_PATH $USER_LOC_PATH
678 $RM -f $USER_LOC_PATH/resolv.conf
679 $NWAMCFG -f $SCRIPT_PATH/create_loc_user
680 # The User location is activated if 'nis' is in a non comment
681 # line of nsswitch.conf.
682 $GREP -v "^#" $USER_LOC_PATH/nsswitch.conf |\
683 $SED -e 's/[^:]*://' |
$GREP nis
>/dev
/null
2>&1
684 if [ $?
-eq 0 ]; then
687 $SVCCFG -s $SMF_FMRI addpg location_upgrade application \
689 $SVCCFG -s $SMF_FMRI setprop location_upgrade
/version
= \
695 # Activate a location. If we've just finished upgrading, and
696 # the User location should be activated, do that (and use nwamadm
697 # to do so, so the enabled property gets set and nwamd knows this
698 # selection has been made). Otherwise, if our location/selected
699 # property has a value, we activate that location; else we activate
700 # the NoNet location as a default value.
702 if [ $activate_user_loc -eq 1 ]; then
703 $NWAMADM enable -p loc User
705 sel_loc
=`$SVCPROP -c -p location/selected $SMF_FMRI 2>/dev/null`
706 if [ $?
-eq 1 ]; then
707 # location hasn't been selected; default to NoNet
711 # If the selected location does not exist, or if we fail
712 # to activate it completely, we fall back to the NoNet
713 # location. Also poke nwamd, so it will check conditions
714 # for a better choice.
716 $NWAMCFG list loc
$sel_loc >/dev
/null
2>&1
717 if [ $?
-eq 1 ]; then
718 echo "location '$sel_loc' doesn't exist"
720 refresh_svc
$NWAM_FMRI
722 # activate selected location
723 if ! activate_loc
$sel_loc; then
724 echo "failed to activate '$sel_loc'"
726 refresh_svc
$NWAM_FMRI