1*fcf3ce44SJohn Forte /* 2*fcf3ce44SJohn Forte * CDDL HEADER START 3*fcf3ce44SJohn Forte * 4*fcf3ce44SJohn Forte * The contents of this file are subject to the terms of the 5*fcf3ce44SJohn Forte * Common Development and Distribution License (the "License"). 6*fcf3ce44SJohn Forte * You may not use this file except in compliance with the License. 7*fcf3ce44SJohn Forte * 8*fcf3ce44SJohn Forte * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9*fcf3ce44SJohn Forte * or http://www.opensolaris.org/os/licensing. 10*fcf3ce44SJohn Forte * See the License for the specific language governing permissions 11*fcf3ce44SJohn Forte * and limitations under the License. 12*fcf3ce44SJohn Forte * 13*fcf3ce44SJohn Forte * When distributing Covered Code, include this CDDL HEADER in each 14*fcf3ce44SJohn Forte * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15*fcf3ce44SJohn Forte * If applicable, add the following below this CDDL HEADER, with the 16*fcf3ce44SJohn Forte * fields enclosed by brackets "[]" replaced with your own identifying 17*fcf3ce44SJohn Forte * information: Portions Copyright [yyyy] [name of copyright owner] 18*fcf3ce44SJohn Forte * 19*fcf3ce44SJohn Forte * CDDL HEADER END 20*fcf3ce44SJohn Forte */ 21*fcf3ce44SJohn Forte /* 22*fcf3ce44SJohn Forte * Copyright 2008 Sun Microsystems, Inc. All rights reserved. 23*fcf3ce44SJohn Forte * Use is subject to license terms. 24*fcf3ce44SJohn Forte */ 25*fcf3ce44SJohn Forte 26*fcf3ce44SJohn Forte 27*fcf3ce44SJohn Forte #include <sys/types.h> 28*fcf3ce44SJohn Forte #include <stdio.h> 29*fcf3ce44SJohn Forte #include <errno.h> 30*fcf3ce44SJohn Forte #include <strings.h> 31*fcf3ce44SJohn Forte #include <stdlib.h> 32*fcf3ce44SJohn Forte #include <unistd.h> 33*fcf3ce44SJohn Forte #include <netdb.h> 34*fcf3ce44SJohn Forte #include <sys/stream.h> 35*fcf3ce44SJohn Forte #include <sys/socket.h> 36*fcf3ce44SJohn Forte #include <netinet/in.h> 37*fcf3ce44SJohn Forte #include <arpa/inet.h> 38*fcf3ce44SJohn Forte #include <ctype.h> 39*fcf3ce44SJohn Forte #include <thread.h> 40*fcf3ce44SJohn Forte #include <pthread.h> 41*fcf3ce44SJohn Forte 42*fcf3ce44SJohn Forte #include <sys/unistat/spcs_s.h> 43*fcf3ce44SJohn Forte #include <sys/unistat/spcs_s_u.h> 44*fcf3ce44SJohn Forte #include <sys/unistat/spcs_s_impl.h> 45*fcf3ce44SJohn Forte #include <sys/unistat/spcs_errors.h> 46*fcf3ce44SJohn Forte 47*fcf3ce44SJohn Forte #include <sys/nsctl/rdc_io.h> 48*fcf3ce44SJohn Forte #include <sys/nsctl/rdc_ioctl.h> 49*fcf3ce44SJohn Forte #include <sys/nsctl/rdc_prot.h> 50*fcf3ce44SJohn Forte #include <sys/nsctl/librdc.h> 51*fcf3ce44SJohn Forte #include <sys/nsctl/rdcrules.h> 52*fcf3ce44SJohn Forte #include <sys/nsctl/rdcerr.h> 53*fcf3ce44SJohn Forte #include <sys/nsctl/cfg.h> 54*fcf3ce44SJohn Forte 55*fcf3ce44SJohn Forte #include <sys/unistat/spcs_dtrinkets.h> 56*fcf3ce44SJohn Forte #include <sys/unistat/spcs_etrinkets.h> 57*fcf3ce44SJohn Forte 58*fcf3ce44SJohn Forte #include <sys/socket.h> 59*fcf3ce44SJohn Forte #include <netinet/in.h> 60*fcf3ce44SJohn Forte #include <arpa/inet.h> 61*fcf3ce44SJohn Forte #include <netinet/tcp.h> 62*fcf3ce44SJohn Forte #include <rpc/rpc_com.h> 63*fcf3ce44SJohn Forte #include <rpc/rpc.h> 64*fcf3ce44SJohn Forte 65*fcf3ce44SJohn Forte struct netbuf svaddr, *svp; 66*fcf3ce44SJohn Forte struct netconfig nconf, *conf; 67*fcf3ce44SJohn Forte struct knetconfig knconf; 68*fcf3ce44SJohn Forte 69*fcf3ce44SJohn Forte /* 70*fcf3ce44SJohn Forte * libdscfg type stuff here 71*fcf3ce44SJohn Forte */ 72*fcf3ce44SJohn Forte extern int sv_enable(CFGFILE *cfg, rdcconfig_t *rdc); 73*fcf3ce44SJohn Forte extern int add_to_rdc_cfg(rdcconfig_t *rdcs); 74*fcf3ce44SJohn Forte extern int remove_from_rdc_cfg(rdcconfig_t *rdcs); 75*fcf3ce44SJohn Forte extern int replace_cfgfield(rdcconfig_t *rdcs, char *field, char *value); 76*fcf3ce44SJohn Forte extern int reverse_in_cfg(rdcconfig_t *rdcs); 77*fcf3ce44SJohn Forte 78*fcf3ce44SJohn Forte rdcconfig_t * 79*fcf3ce44SJohn Forte rdc_dup_config(rdcconfig_t *orig) 80*fcf3ce44SJohn Forte { 81*fcf3ce44SJohn Forte rdcconfig_t *rc; 82*fcf3ce44SJohn Forte 83*fcf3ce44SJohn Forte rc = (rdcconfig_t *)calloc(1, sizeof (*rc)); 84*fcf3ce44SJohn Forte if (!rc) { 85*fcf3ce44SJohn Forte rdc_set_error(NULL, RDC_OS, RDC_FATAL, NULL); 86*fcf3ce44SJohn Forte return (NULL); 87*fcf3ce44SJohn Forte } 88*fcf3ce44SJohn Forte 89*fcf3ce44SJohn Forte *rc = *orig; 90*fcf3ce44SJohn Forte rc->next = NULL; /* don't want to hook into wrong chaing */ 91*fcf3ce44SJohn Forte return (rc); 92*fcf3ce44SJohn Forte } 93*fcf3ce44SJohn Forte 94*fcf3ce44SJohn Forte /* 95*fcf3ce44SJohn Forte * takes in a chain of rdcconfig_t's and a chain 96*fcf3ce44SJohn Forte * of rdc_rc_t's, checks for success in the rdc_rc_t, 97*fcf3ce44SJohn Forte * then adds the corresponding rdcconfig_t to the return 98*fcf3ce44SJohn Forte * chain. 99*fcf3ce44SJohn Forte */ 100*fcf3ce44SJohn Forte rdcconfig_t * 101*fcf3ce44SJohn Forte chain_successful(rdcconfig_t *rdcs, rdc_rc_t *rcs) 102*fcf3ce44SJohn Forte { 103*fcf3ce44SJohn Forte rdc_rc_t *rcp; 104*fcf3ce44SJohn Forte rdcconfig_t *rdcp; 105*fcf3ce44SJohn Forte rdcconfig_t *ret = NULL; 106*fcf3ce44SJohn Forte rdcconfig_t *retp = NULL; 107*fcf3ce44SJohn Forte 108*fcf3ce44SJohn Forte rcp = rcs; 109*fcf3ce44SJohn Forte rdcp = rdcs; 110*fcf3ce44SJohn Forte 111*fcf3ce44SJohn Forte while (rcp) { 112*fcf3ce44SJohn Forte if (rcp->rc == 0) { 113*fcf3ce44SJohn Forte if ((ret == NULL) && (rdcp->persist)) { 114*fcf3ce44SJohn Forte retp = ret = rdc_dup_config(rdcp); 115*fcf3ce44SJohn Forte 116*fcf3ce44SJohn Forte } else if ((ret) && (rdcp->persist)) { 117*fcf3ce44SJohn Forte retp->next = rdc_dup_config(rdcp); 118*fcf3ce44SJohn Forte retp = retp->next; 119*fcf3ce44SJohn Forte } 120*fcf3ce44SJohn Forte } 121*fcf3ce44SJohn Forte rcp = rcp->next; 122*fcf3ce44SJohn Forte rdcp = rdcp->next; 123*fcf3ce44SJohn Forte } 124*fcf3ce44SJohn Forte return (ret); 125*fcf3ce44SJohn Forte 126*fcf3ce44SJohn Forte } 127*fcf3ce44SJohn Forte 128*fcf3ce44SJohn Forte rdc_set_t 129*fcf3ce44SJohn Forte config2set(rdcconfig_t *rdc) 130*fcf3ce44SJohn Forte { 131*fcf3ce44SJohn Forte rdc_set_t urdc; 132*fcf3ce44SJohn Forte 133*fcf3ce44SJohn Forte bzero(&urdc, sizeof (rdc_set_t)); 134*fcf3ce44SJohn Forte strncpy(urdc.primary.intf, rdc->phost, MAX_RDC_HOST_SIZE); 135*fcf3ce44SJohn Forte strncpy(urdc.primary.file, rdc->pfile, NSC_MAXPATH); 136*fcf3ce44SJohn Forte strncpy(urdc.primary.bitmap, rdc->pbmp, NSC_MAXPATH); 137*fcf3ce44SJohn Forte strncpy(urdc.secondary.intf, rdc->shost, MAX_RDC_HOST_SIZE); 138*fcf3ce44SJohn Forte strncpy(urdc.secondary.file, rdc->sfile, NSC_MAXPATH); 139*fcf3ce44SJohn Forte strncpy(urdc.secondary.bitmap, rdc->sbmp, NSC_MAXPATH); 140*fcf3ce44SJohn Forte strncpy(urdc.group_name, rdc->group, NSC_MAXPATH); 141*fcf3ce44SJohn Forte 142*fcf3ce44SJohn Forte return (urdc); 143*fcf3ce44SJohn Forte } 144*fcf3ce44SJohn Forte 145*fcf3ce44SJohn Forte rdc_rc_t * 146*fcf3ce44SJohn Forte new_rc() 147*fcf3ce44SJohn Forte { 148*fcf3ce44SJohn Forte rdc_rc_t *rc; 149*fcf3ce44SJohn Forte 150*fcf3ce44SJohn Forte rc = (rdc_rc_t *)calloc(1, sizeof (*rc)); 151*fcf3ce44SJohn Forte if (rc == NULL) { 152*fcf3ce44SJohn Forte rdc_set_error(NULL, RDC_OS, RDC_FATAL, NULL); 153*fcf3ce44SJohn Forte return (NULL); 154*fcf3ce44SJohn Forte } 155*fcf3ce44SJohn Forte return (rc); 156*fcf3ce44SJohn Forte } 157*fcf3ce44SJohn Forte 158*fcf3ce44SJohn Forte rdc_rc_t 159*fcf3ce44SJohn Forte rdc_config(rdc_config_t *rdccfg) 160*fcf3ce44SJohn Forte { 161*fcf3ce44SJohn Forte rdc_rc_t rc; 162*fcf3ce44SJohn Forte rdc_set_t *set; 163*fcf3ce44SJohn Forte spcs_s_info_t ustatus; 164*fcf3ce44SJohn Forte 165*fcf3ce44SJohn Forte bzero(&rc, sizeof (rc)); 166*fcf3ce44SJohn Forte ustatus = spcs_s_ucreate(); 167*fcf3ce44SJohn Forte 168*fcf3ce44SJohn Forte if (self_check(rdccfg->rdc_set->primary.intf)) { 169*fcf3ce44SJohn Forte rdccfg->options |= RDC_OPT_PRIMARY; 170*fcf3ce44SJohn Forte /* this needs changin if we do campus */ 171*fcf3ce44SJohn Forte rdccfg->rdc_set->direct_file[0] = 0; 172*fcf3ce44SJohn Forte } else { 173*fcf3ce44SJohn Forte rdccfg->options |= RDC_OPT_SECONDARY; 174*fcf3ce44SJohn Forte } 175*fcf3ce44SJohn Forte 176*fcf3ce44SJohn Forte /* set up return stuff.. */ 177*fcf3ce44SJohn Forte set = &rdccfg->rdc_set[0]; 178*fcf3ce44SJohn Forte strncpy(rc.set.phost, set->primary.intf, MAX_RDC_HOST_SIZE); 179*fcf3ce44SJohn Forte strncpy(rc.set.pfile, set->primary.file, NSC_MAXPATH); 180*fcf3ce44SJohn Forte strncpy(rc.set.shost, set->secondary.intf, MAX_RDC_HOST_SIZE); 181*fcf3ce44SJohn Forte strncpy(rc.set.sfile, set->secondary.file, NSC_MAXPATH); 182*fcf3ce44SJohn Forte 183*fcf3ce44SJohn Forte rc.rc = RDC_IOCTL(RDC_CONFIG, rdccfg, NULL, 0, 0, 0, ustatus); 184*fcf3ce44SJohn Forte 185*fcf3ce44SJohn Forte if (rc.rc < 0) { 186*fcf3ce44SJohn Forte rdc_set_error(&ustatus, RDC_SPCS, 0, 0); 187*fcf3ce44SJohn Forte strncpy(rc.msg, rdc_error(NULL), RDC_ERR_SIZE); 188*fcf3ce44SJohn Forte } 189*fcf3ce44SJohn Forte 190*fcf3ce44SJohn Forte return (rc); 191*fcf3ce44SJohn Forte } 192*fcf3ce44SJohn Forte 193*fcf3ce44SJohn Forte void * 194*fcf3ce44SJohn Forte rdc_mtconfig(void *rdc) 195*fcf3ce44SJohn Forte { 196*fcf3ce44SJohn Forte rdc_rc_t *rc[1]; 197*fcf3ce44SJohn Forte rdc_set_t *set; 198*fcf3ce44SJohn Forte spcs_s_info_t ustatus; 199*fcf3ce44SJohn Forte rdc_config_t *rdccfg = (rdc_config_t *)rdc; 200*fcf3ce44SJohn Forte 201*fcf3ce44SJohn Forte ustatus = spcs_s_ucreate(); 202*fcf3ce44SJohn Forte 203*fcf3ce44SJohn Forte if (self_check(rdccfg->rdc_set->primary.intf)) { 204*fcf3ce44SJohn Forte rdccfg->options |= RDC_OPT_PRIMARY; 205*fcf3ce44SJohn Forte /* this needs changin if we do campus */ 206*fcf3ce44SJohn Forte rdccfg->rdc_set->direct_file[0] = 0; 207*fcf3ce44SJohn Forte } else { 208*fcf3ce44SJohn Forte rdccfg->options |= RDC_OPT_SECONDARY; 209*fcf3ce44SJohn Forte } 210*fcf3ce44SJohn Forte 211*fcf3ce44SJohn Forte set = &rdccfg->rdc_set[0]; 212*fcf3ce44SJohn Forte *rc = new_rc(); 213*fcf3ce44SJohn Forte 214*fcf3ce44SJohn Forte strncpy(rc[0]->set.phost, set->primary.intf, MAX_RDC_HOST_SIZE); 215*fcf3ce44SJohn Forte strncpy(rc[0]->set.pfile, set->primary.file, NSC_MAXPATH); 216*fcf3ce44SJohn Forte strncpy(rc[0]->set.pbmp, set->primary.bitmap, NSC_MAXPATH); 217*fcf3ce44SJohn Forte strncpy(rc[0]->set.shost, set->secondary.intf, MAX_RDC_HOST_SIZE); 218*fcf3ce44SJohn Forte strncpy(rc[0]->set.sfile, set->secondary.file, NSC_MAXPATH); 219*fcf3ce44SJohn Forte strncpy(rc[0]->set.sbmp, set->secondary.bitmap, NSC_MAXPATH); 220*fcf3ce44SJohn Forte 221*fcf3ce44SJohn Forte rc[0]->rc = RDC_IOCTL(RDC_CONFIG, rdccfg, NULL, 0, 0, 0, ustatus); 222*fcf3ce44SJohn Forte 223*fcf3ce44SJohn Forte if (rc[0]->rc < 0) { 224*fcf3ce44SJohn Forte rdc_set_error(&ustatus, RDC_SPCS, 0, 0); 225*fcf3ce44SJohn Forte strncpy(rc[0]->msg, rdc_error(NULL), RDC_ERR_SIZE); 226*fcf3ce44SJohn Forte } 227*fcf3ce44SJohn Forte 228*fcf3ce44SJohn Forte sleep(1); /* give thr_join a chance to be called */ 229*fcf3ce44SJohn Forte free(rdccfg); 230*fcf3ce44SJohn Forte thr_exit((void **) *rc); 231*fcf3ce44SJohn Forte return (NULL); 232*fcf3ce44SJohn Forte } 233*fcf3ce44SJohn Forte int 234*fcf3ce44SJohn Forte populate_addrs(rdc_set_t *urdc, int isenable) 235*fcf3ce44SJohn Forte { 236*fcf3ce44SJohn Forte struct t_info tinfo; 237*fcf3ce44SJohn Forte struct hostent *hp; 238*fcf3ce44SJohn Forte char toname[MAX_RDC_HOST_SIZE]; 239*fcf3ce44SJohn Forte char fromname[MAX_RDC_HOST_SIZE]; 240*fcf3ce44SJohn Forte 241*fcf3ce44SJohn Forte strncpy(fromname, urdc->primary.intf, MAX_RDC_HOST_SIZE); 242*fcf3ce44SJohn Forte strncpy(toname, urdc->secondary.intf, MAX_RDC_HOST_SIZE); 243*fcf3ce44SJohn Forte 244*fcf3ce44SJohn Forte if ((fromname[0] == '\0') || (fromname[0] == '\0')) { 245*fcf3ce44SJohn Forte rdc_set_error(NULL, RDC_INTERNAL, RDC_FATAL, 246*fcf3ce44SJohn Forte "NULL hostname recieved"); 247*fcf3ce44SJohn Forte return (-1); 248*fcf3ce44SJohn Forte } 249*fcf3ce44SJohn Forte 250*fcf3ce44SJohn Forte hp = gethost_byname(fromname); 251*fcf3ce44SJohn Forte strncpy(fromname, hp->h_name, MAX_RDC_HOST_SIZE); 252*fcf3ce44SJohn Forte hp = gethost_byname(toname); 253*fcf3ce44SJohn Forte strncpy(toname, hp->h_name, MAX_RDC_HOST_SIZE); 254*fcf3ce44SJohn Forte 255*fcf3ce44SJohn Forte if (self_check(fromname) && self_check(toname)) { 256*fcf3ce44SJohn Forte rdc_set_error(NULL, RDC_INTERNAL, RDC_FATAL, ""); 257*fcf3ce44SJohn Forte } 258*fcf3ce44SJohn Forte 259*fcf3ce44SJohn Forte if (isenable) { 260*fcf3ce44SJohn Forte svp = get_addr(toname, RDC_PROGRAM, RDC_VERS_MIN, 261*fcf3ce44SJohn Forte &conf, NULL, "rdc", &tinfo, 0); 262*fcf3ce44SJohn Forte if (svp == NULL) 263*fcf3ce44SJohn Forte return (-1); 264*fcf3ce44SJohn Forte svaddr = *svp; 265*fcf3ce44SJohn Forte } else { 266*fcf3ce44SJohn Forte bzero(&svaddr, sizeof (svaddr)); 267*fcf3ce44SJohn Forte } 268*fcf3ce44SJohn Forte 269*fcf3ce44SJohn Forte urdc->secondary.addr.len = svaddr.len; 270*fcf3ce44SJohn Forte urdc->secondary.addr.maxlen = svaddr.maxlen; 271*fcf3ce44SJohn Forte urdc->secondary.addr.buf = (void*)svaddr.buf; 272*fcf3ce44SJohn Forte 273*fcf3ce44SJohn Forte if (isenable) { 274*fcf3ce44SJohn Forte svp = get_addr(fromname, RDC_PROGRAM, RDC_VERS_MIN, 275*fcf3ce44SJohn Forte &conf, NULL, "rdc", &tinfo, 0); 276*fcf3ce44SJohn Forte if (svp == NULL) 277*fcf3ce44SJohn Forte return (-1); 278*fcf3ce44SJohn Forte svaddr = *svp; 279*fcf3ce44SJohn Forte } else { 280*fcf3ce44SJohn Forte bzero(&svaddr, sizeof (svaddr)); 281*fcf3ce44SJohn Forte } 282*fcf3ce44SJohn Forte 283*fcf3ce44SJohn Forte urdc->primary.addr.len = svaddr.len; 284*fcf3ce44SJohn Forte urdc->primary.addr.maxlen = svaddr.maxlen; 285*fcf3ce44SJohn Forte urdc->primary.addr.buf = (void*)svaddr.buf; 286*fcf3ce44SJohn Forte 287*fcf3ce44SJohn Forte if (isenable) { 288*fcf3ce44SJohn Forte convert_nconf_to_knconf(conf, &knconf); 289*fcf3ce44SJohn Forte urdc->netconfig = &knconf; 290*fcf3ce44SJohn Forte } else { 291*fcf3ce44SJohn Forte urdc->netconfig = NULL; 292*fcf3ce44SJohn Forte } 293*fcf3ce44SJohn Forte urdc->syshostid = (int32_t)gethostid(); 294*fcf3ce44SJohn Forte 295*fcf3ce44SJohn Forte return (1); 296*fcf3ce44SJohn Forte 297*fcf3ce44SJohn Forte } 298*fcf3ce44SJohn Forte void 299*fcf3ce44SJohn Forte rdc_free_config(rdcconfig_t *rdc, int all) 300*fcf3ce44SJohn Forte { 301*fcf3ce44SJohn Forte rdcconfig_t *rdcp; 302*fcf3ce44SJohn Forte rdcconfig_t *rdcq; 303*fcf3ce44SJohn Forte 304*fcf3ce44SJohn Forte rdcp = rdc; 305*fcf3ce44SJohn Forte if (all == RDC_FREEONE) { 306*fcf3ce44SJohn Forte free(rdcp); 307*fcf3ce44SJohn Forte } else while (rdcp) { 308*fcf3ce44SJohn Forte rdcq = rdcp->next; 309*fcf3ce44SJohn Forte free(rdcp); 310*fcf3ce44SJohn Forte rdcp = rdcq; 311*fcf3ce44SJohn Forte } 312*fcf3ce44SJohn Forte rdc = NULL; 313*fcf3ce44SJohn Forte } 314*fcf3ce44SJohn Forte 315*fcf3ce44SJohn Forte void 316*fcf3ce44SJohn Forte rdc_free_rclist(rdc_rc_t *rc) { 317*fcf3ce44SJohn Forte rdc_rc_t *rcp, *rcq; 318*fcf3ce44SJohn Forte 319*fcf3ce44SJohn Forte rcp = rc; 320*fcf3ce44SJohn Forte while (rcp) { 321*fcf3ce44SJohn Forte rcq = rcp->next; 322*fcf3ce44SJohn Forte free(rcp); 323*fcf3ce44SJohn Forte rcp = rcq; 324*fcf3ce44SJohn Forte } 325*fcf3ce44SJohn Forte 326*fcf3ce44SJohn Forte } 327*fcf3ce44SJohn Forte /*ARGSUSED*/ 328*fcf3ce44SJohn Forte rdcconfig_t * 329*fcf3ce44SJohn Forte rdc_alloc_config(const char *phost, const char *pfile, 330*fcf3ce44SJohn Forte const char *pbmp, const char *shost, const char *sfile, const char *sbmp, 331*fcf3ce44SJohn Forte const char *mode, const char *group, const char *ctag, const char *options, 332*fcf3ce44SJohn Forte int persist) 333*fcf3ce44SJohn Forte { 334*fcf3ce44SJohn Forte rdcconfig_t *rc; 335*fcf3ce44SJohn Forte 336*fcf3ce44SJohn Forte rc = (rdcconfig_t *)calloc(1, sizeof (*rc)); 337*fcf3ce44SJohn Forte if (!rc) { 338*fcf3ce44SJohn Forte rdc_set_error(NULL, RDC_OS, RDC_FATAL, NULL); 339*fcf3ce44SJohn Forte return (NULL); 340*fcf3ce44SJohn Forte } 341*fcf3ce44SJohn Forte if (phost) 342*fcf3ce44SJohn Forte strncpy(rc->phost, phost, NSC_MAXPATH); 343*fcf3ce44SJohn Forte if (pfile) 344*fcf3ce44SJohn Forte strncpy(rc->pfile, pfile, NSC_MAXPATH); 345*fcf3ce44SJohn Forte if (pbmp) 346*fcf3ce44SJohn Forte strncpy(rc->pbmp, pbmp, NSC_MAXPATH); 347*fcf3ce44SJohn Forte if (shost) 348*fcf3ce44SJohn Forte strncpy(rc->shost, shost, NSC_MAXPATH); 349*fcf3ce44SJohn Forte if (sfile) 350*fcf3ce44SJohn Forte strncpy(rc->sfile, sfile, NSC_MAXPATH); 351*fcf3ce44SJohn Forte if (sbmp) 352*fcf3ce44SJohn Forte strncpy(rc->sbmp, sbmp, NSC_MAXPATH); 353*fcf3ce44SJohn Forte 354*fcf3ce44SJohn Forte strncpy(rc->direct, "ip", 2); 355*fcf3ce44SJohn Forte 356*fcf3ce44SJohn Forte if (mode) 357*fcf3ce44SJohn Forte strncpy(rc->mode, mode, NSC_MAXPATH); 358*fcf3ce44SJohn Forte if (ctag) 359*fcf3ce44SJohn Forte strncpy(rc->ctag, ctag, NSC_MAXPATH); 360*fcf3ce44SJohn Forte if (options) 361*fcf3ce44SJohn Forte strncpy(rc->options, options, NSC_MAXPATH); 362*fcf3ce44SJohn Forte 363*fcf3ce44SJohn Forte rc->persist = persist; 364*fcf3ce44SJohn Forte rc->next = NULL; 365*fcf3ce44SJohn Forte 366*fcf3ce44SJohn Forte return (rc); 367*fcf3ce44SJohn Forte 368*fcf3ce44SJohn Forte } 369*fcf3ce44SJohn Forte 370*fcf3ce44SJohn Forte void 371*fcf3ce44SJohn Forte populate_rc(rdc_rc_t *rcp, rdcconfig_t *rdcp) 372*fcf3ce44SJohn Forte { 373*fcf3ce44SJohn Forte rcp->rc = -1; 374*fcf3ce44SJohn Forte strncpy(rcp->msg, rdc_error(NULL), RDC_ERR_SIZE); 375*fcf3ce44SJohn Forte strncpy(rcp->set.phost, rdcp->phost, NSC_MAXPATH); 376*fcf3ce44SJohn Forte strncpy(rcp->set.pfile, rdcp->pfile, NSC_MAXPATH); 377*fcf3ce44SJohn Forte strncpy(rcp->set.shost, rdcp->shost, NSC_MAXPATH); 378*fcf3ce44SJohn Forte strncpy(rcp->set.sfile, rdcp->sfile, NSC_MAXPATH); 379*fcf3ce44SJohn Forte } 380*fcf3ce44SJohn Forte 381*fcf3ce44SJohn Forte /* 382*fcf3ce44SJohn Forte * rdc_enable 383*fcf3ce44SJohn Forte * return values 384*fcf3ce44SJohn Forte * NULL on error 385*fcf3ce44SJohn Forte * pointer to rdc_rc_t list of return values 386*fcf3ce44SJohn Forte */ 387*fcf3ce44SJohn Forte rdc_rc_t * 388*fcf3ce44SJohn Forte rdc_enable(rdcconfig_t *rdc) 389*fcf3ce44SJohn Forte { 390*fcf3ce44SJohn Forte rdc_config_t rdccfg; 391*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 392*fcf3ce44SJohn Forte rdcconfig_t *cfg_rdcs = NULL; 393*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 394*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 395*fcf3ce44SJohn Forte 396*fcf3ce44SJohn Forte rdcp = rdc; 397*fcf3ce44SJohn Forte rc = new_rc(); 398*fcf3ce44SJohn Forte if (!rc) { /* error already set */ 399*fcf3ce44SJohn Forte return (NULL); 400*fcf3ce44SJohn Forte } 401*fcf3ce44SJohn Forte rcp = rc; 402*fcf3ce44SJohn Forte while (rdcp) { 403*fcf3ce44SJohn Forte if (!rdcp->mode) { 404*fcf3ce44SJohn Forte rdc_set_error(NULL, RDC_INTERNAL, RDC_NONFATAL, 405*fcf3ce44SJohn Forte RDC_EINVAL); 406*fcf3ce44SJohn Forte return (NULL); 407*fcf3ce44SJohn Forte } 408*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 409*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdcp); 410*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_ENABLE; 411*fcf3ce44SJohn Forte rdccfg.options = RDC_OPT_SETBMP; 412*fcf3ce44SJohn Forte if (strncmp(rdcp->mode, "sync", NSC_MAXPATH) == 0) { 413*fcf3ce44SJohn Forte rdccfg.options |= RDC_OPT_SYNC; 414*fcf3ce44SJohn Forte } else if (strncmp(rdc->mode, "async", NSC_MAXPATH) == 0) { 415*fcf3ce44SJohn Forte rdccfg.options |= RDC_OPT_ASYNC; 416*fcf3ce44SJohn Forte } else { 417*fcf3ce44SJohn Forte rdc_set_error(NULL, RDC_INTERNAL, RDC_NONFATAL, 418*fcf3ce44SJohn Forte RDC_EINVAL); 419*fcf3ce44SJohn Forte return (NULL); 420*fcf3ce44SJohn Forte } 421*fcf3ce44SJohn Forte 422*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 1); 423*fcf3ce44SJohn Forte 424*fcf3ce44SJohn Forte if (can_enable(rdcp)) { 425*fcf3ce44SJohn Forte /* do the operation */ 426*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 427*fcf3ce44SJohn Forte 428*fcf3ce44SJohn Forte } else { /* set up what rdc_config would've set up */ 429*fcf3ce44SJohn Forte 430*fcf3ce44SJohn Forte populate_rc(rcp, rdcp); 431*fcf3ce44SJohn Forte 432*fcf3ce44SJohn Forte } 433*fcf3ce44SJohn Forte if ((rcp->rc == 0) && (!rdcp->persist)) { 434*fcf3ce44SJohn Forte /* 435*fcf3ce44SJohn Forte * if we are not persisting, do this now, 436*fcf3ce44SJohn Forte * otherwise we will do it when 437*fcf3ce44SJohn Forte * we have a lock on the cfg in add_to_rdc_cfg 438*fcf3ce44SJohn Forte */ 439*fcf3ce44SJohn Forte sv_enable(NULL, rdcp); 440*fcf3ce44SJohn Forte } 441*fcf3ce44SJohn Forte 442*fcf3ce44SJohn Forte rdcp = rdcp->next; 443*fcf3ce44SJohn Forte if (!rdcp) 444*fcf3ce44SJohn Forte break; 445*fcf3ce44SJohn Forte 446*fcf3ce44SJohn Forte rcp->next = new_rc(); 447*fcf3ce44SJohn Forte rcp = rcp->next; 448*fcf3ce44SJohn Forte if (!rcp) { 449*fcf3ce44SJohn Forte /* dont free here, return what you have */ 450*fcf3ce44SJohn Forte break; 451*fcf3ce44SJohn Forte } 452*fcf3ce44SJohn Forte } 453*fcf3ce44SJohn Forte 454*fcf3ce44SJohn Forte /* 455*fcf3ce44SJohn Forte * travel the rc chain and rdc chain checking results, 456*fcf3ce44SJohn Forte * building a new chain, and updating dscfg 457*fcf3ce44SJohn Forte */ 458*fcf3ce44SJohn Forte rcp = rc; 459*fcf3ce44SJohn Forte rdcp = rdc; 460*fcf3ce44SJohn Forte 461*fcf3ce44SJohn Forte cfg_rdcs = chain_successful(rdcp, rcp); 462*fcf3ce44SJohn Forte 463*fcf3ce44SJohn Forte if (add_to_rdc_cfg(cfg_rdcs) < 0) { 464*fcf3ce44SJohn Forte /* XXX should disable or something here */ 465*fcf3ce44SJohn Forte return (rc); 466*fcf3ce44SJohn Forte } 467*fcf3ce44SJohn Forte rdc_free_config(cfg_rdcs, RDC_FREEALL); 468*fcf3ce44SJohn Forte return (rc); 469*fcf3ce44SJohn Forte 470*fcf3ce44SJohn Forte } 471*fcf3ce44SJohn Forte 472*fcf3ce44SJohn Forte rdc_rc_t * 473*fcf3ce44SJohn Forte rdc_enable_clrbmp(rdcconfig_t *rdc) 474*fcf3ce44SJohn Forte { 475*fcf3ce44SJohn Forte rdc_config_t rdccfg; 476*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 477*fcf3ce44SJohn Forte rdcconfig_t *cfg_rdcs = NULL; 478*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 479*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 480*fcf3ce44SJohn Forte 481*fcf3ce44SJohn Forte rdcp = rdc; 482*fcf3ce44SJohn Forte rc = (rdc_rc_t *)calloc(1, sizeof (rdc_rc_t)); 483*fcf3ce44SJohn Forte if (!rc) { 484*fcf3ce44SJohn Forte rdc_set_error(NULL, RDC_OS, RDC_FATAL, NULL); 485*fcf3ce44SJohn Forte return (NULL); 486*fcf3ce44SJohn Forte } 487*fcf3ce44SJohn Forte rcp = rc; 488*fcf3ce44SJohn Forte while (rdcp) { 489*fcf3ce44SJohn Forte if (!rdcp->mode) { 490*fcf3ce44SJohn Forte rdc_set_error(NULL, RDC_INTERNAL, RDC_NONFATAL, 491*fcf3ce44SJohn Forte RDC_EINVAL); 492*fcf3ce44SJohn Forte return (NULL); 493*fcf3ce44SJohn Forte } 494*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 495*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdcp); 496*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_ENABLE; 497*fcf3ce44SJohn Forte rdccfg.options = RDC_OPT_CLRBMP; 498*fcf3ce44SJohn Forte if (strncmp(rdcp->mode, "sync", NSC_MAXPATH) == 0) { 499*fcf3ce44SJohn Forte rdccfg.options |= RDC_OPT_SYNC; 500*fcf3ce44SJohn Forte } else if (strncmp(rdc->mode, "async", NSC_MAXPATH) == 0) { 501*fcf3ce44SJohn Forte rdccfg.options |= RDC_OPT_ASYNC; 502*fcf3ce44SJohn Forte } else { 503*fcf3ce44SJohn Forte rdc_set_error(NULL, RDC_INTERNAL, RDC_NONFATAL, 504*fcf3ce44SJohn Forte RDC_EINVAL); 505*fcf3ce44SJohn Forte return (NULL); 506*fcf3ce44SJohn Forte } 507*fcf3ce44SJohn Forte 508*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 1); 509*fcf3ce44SJohn Forte 510*fcf3ce44SJohn Forte if (can_enable(rdcp)) { 511*fcf3ce44SJohn Forte /* do the operation */ 512*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 513*fcf3ce44SJohn Forte 514*fcf3ce44SJohn Forte } else { /* set up what rdc_config would've set up */ 515*fcf3ce44SJohn Forte 516*fcf3ce44SJohn Forte populate_rc(rcp, rdcp); 517*fcf3ce44SJohn Forte 518*fcf3ce44SJohn Forte } 519*fcf3ce44SJohn Forte rdcp = rdcp->next; 520*fcf3ce44SJohn Forte if (!rdcp) 521*fcf3ce44SJohn Forte break; 522*fcf3ce44SJohn Forte 523*fcf3ce44SJohn Forte rcp->next = (rdc_rc_t *)calloc(1, sizeof (rdc_rc_t)); 524*fcf3ce44SJohn Forte rcp = rcp->next; 525*fcf3ce44SJohn Forte if (!rcp) 526*fcf3ce44SJohn Forte break; 527*fcf3ce44SJohn Forte } 528*fcf3ce44SJohn Forte 529*fcf3ce44SJohn Forte /* 530*fcf3ce44SJohn Forte * travel the rc chain and rdc chain checking results, 531*fcf3ce44SJohn Forte * building a new chain, and updating dscfg 532*fcf3ce44SJohn Forte */ 533*fcf3ce44SJohn Forte rcp = rc; 534*fcf3ce44SJohn Forte rdcp = rdc; 535*fcf3ce44SJohn Forte 536*fcf3ce44SJohn Forte cfg_rdcs = chain_successful(rdcp, rcp); 537*fcf3ce44SJohn Forte 538*fcf3ce44SJohn Forte if (add_to_rdc_cfg(cfg_rdcs) < 0) { 539*fcf3ce44SJohn Forte /* XXX should disable or something here */ 540*fcf3ce44SJohn Forte return (rc); 541*fcf3ce44SJohn Forte } 542*fcf3ce44SJohn Forte rdc_free_config(cfg_rdcs, RDC_FREEALL); 543*fcf3ce44SJohn Forte 544*fcf3ce44SJohn Forte return (rc); 545*fcf3ce44SJohn Forte 546*fcf3ce44SJohn Forte } 547*fcf3ce44SJohn Forte 548*fcf3ce44SJohn Forte rdc_rc_t * 549*fcf3ce44SJohn Forte rdc_disable(rdcconfig_t *rdc) 550*fcf3ce44SJohn Forte { 551*fcf3ce44SJohn Forte rdc_config_t rdccfg; 552*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 553*fcf3ce44SJohn Forte rdcconfig_t *cfg_rdcs = NULL; 554*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 555*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 556*fcf3ce44SJohn Forte 557*fcf3ce44SJohn Forte rdcp = rdc; 558*fcf3ce44SJohn Forte rc = new_rc(); 559*fcf3ce44SJohn Forte if (!rc) { 560*fcf3ce44SJohn Forte return (NULL); 561*fcf3ce44SJohn Forte } 562*fcf3ce44SJohn Forte rcp = rc; 563*fcf3ce44SJohn Forte 564*fcf3ce44SJohn Forte while (rdcp) { 565*fcf3ce44SJohn Forte 566*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 567*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdcp); 568*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_DISABLE; 569*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 570*fcf3ce44SJohn Forte 571*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 572*fcf3ce44SJohn Forte 573*fcf3ce44SJohn Forte rdcp = rdcp->next; 574*fcf3ce44SJohn Forte if (!rdcp) 575*fcf3ce44SJohn Forte break; 576*fcf3ce44SJohn Forte 577*fcf3ce44SJohn Forte rcp->next = new_rc(); 578*fcf3ce44SJohn Forte rcp = rcp->next; 579*fcf3ce44SJohn Forte if (!rcp) 580*fcf3ce44SJohn Forte return (rc); 581*fcf3ce44SJohn Forte 582*fcf3ce44SJohn Forte } 583*fcf3ce44SJohn Forte rcp = rc; 584*fcf3ce44SJohn Forte rdcp = rdc; 585*fcf3ce44SJohn Forte 586*fcf3ce44SJohn Forte cfg_rdcs = chain_successful(rdcp, rcp); 587*fcf3ce44SJohn Forte 588*fcf3ce44SJohn Forte remove_from_rdc_cfg(cfg_rdcs); 589*fcf3ce44SJohn Forte 590*fcf3ce44SJohn Forte rdc_free_config(cfg_rdcs, RDC_FREEALL); 591*fcf3ce44SJohn Forte 592*fcf3ce44SJohn Forte return (rc); 593*fcf3ce44SJohn Forte } 594*fcf3ce44SJohn Forte 595*fcf3ce44SJohn Forte rdc_rc_t * 596*fcf3ce44SJohn Forte rdc_log(rdcconfig_t *rdc) 597*fcf3ce44SJohn Forte { 598*fcf3ce44SJohn Forte rdc_config_t rdccfg; 599*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 600*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 601*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 602*fcf3ce44SJohn Forte 603*fcf3ce44SJohn Forte rdcp = rdc; 604*fcf3ce44SJohn Forte rc = new_rc(); 605*fcf3ce44SJohn Forte if (!rc) { 606*fcf3ce44SJohn Forte return (NULL); 607*fcf3ce44SJohn Forte } 608*fcf3ce44SJohn Forte rcp = rc; 609*fcf3ce44SJohn Forte 610*fcf3ce44SJohn Forte while (rdcp) { 611*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 612*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdcp); 613*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_LOG; 614*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 615*fcf3ce44SJohn Forte 616*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 617*fcf3ce44SJohn Forte 618*fcf3ce44SJohn Forte rdcp = rdcp->next; 619*fcf3ce44SJohn Forte if (!rdcp) 620*fcf3ce44SJohn Forte break; 621*fcf3ce44SJohn Forte 622*fcf3ce44SJohn Forte rcp->next = new_rc(); 623*fcf3ce44SJohn Forte rcp = rcp->next; 624*fcf3ce44SJohn Forte if (!rcp) 625*fcf3ce44SJohn Forte break; 626*fcf3ce44SJohn Forte } 627*fcf3ce44SJohn Forte return (rc); 628*fcf3ce44SJohn Forte } 629*fcf3ce44SJohn Forte 630*fcf3ce44SJohn Forte rdc_rc_t * 631*fcf3ce44SJohn Forte rdc_usync(rdcconfig_t *rdc) 632*fcf3ce44SJohn Forte { 633*fcf3ce44SJohn Forte rdc_config_t *rdccfg; 634*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 635*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 636*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 637*fcf3ce44SJohn Forte rdc_rc_t *tmprc; 638*fcf3ce44SJohn Forte int trc; 639*fcf3ce44SJohn Forte 640*fcf3ce44SJohn Forte rdcp = rdc; 641*fcf3ce44SJohn Forte 642*fcf3ce44SJohn Forte while (rdcp) { 643*fcf3ce44SJohn Forte /* freed in rdc_mtconfig */ 644*fcf3ce44SJohn Forte rdccfg = (rdc_config_t *)calloc(1, sizeof (rdc_config_t)); 645*fcf3ce44SJohn Forte rdccfg->rdc_set[0] = config2set(rdcp); 646*fcf3ce44SJohn Forte rdccfg->command = RDC_CMD_COPY; 647*fcf3ce44SJohn Forte rdccfg->options = RDC_OPT_UPDATE|RDC_OPT_FORWARD; 648*fcf3ce44SJohn Forte populate_addrs(&rdccfg->rdc_set[0], 0); 649*fcf3ce44SJohn Forte trc = thr_create(NULL, 0, rdc_mtconfig, 650*fcf3ce44SJohn Forte (void **) rdccfg, THR_BOUND, NULL); 651*fcf3ce44SJohn Forte rdcp = rdcp->next; 652*fcf3ce44SJohn Forte if (!rdcp) 653*fcf3ce44SJohn Forte break; 654*fcf3ce44SJohn Forte 655*fcf3ce44SJohn Forte } 656*fcf3ce44SJohn Forte 657*fcf3ce44SJohn Forte /* 658*fcf3ce44SJohn Forte * collect status here from thr_join-status, 659*fcf3ce44SJohn Forte * and add to rdc_rc_t chain ? 660*fcf3ce44SJohn Forte * this will block, but caller could always thread too 661*fcf3ce44SJohn Forte */ 662*fcf3ce44SJohn Forte while (thr_join(NULL, NULL, (void**) &tmprc) == 0) { 663*fcf3ce44SJohn Forte if (rc == NULL) { 664*fcf3ce44SJohn Forte rcp = rc = (rdc_rc_t *)tmprc; 665*fcf3ce44SJohn Forte } else { 666*fcf3ce44SJohn Forte rcp->next = (rdc_rc_t *)tmprc; 667*fcf3ce44SJohn Forte rcp = rcp->next; 668*fcf3ce44SJohn Forte } 669*fcf3ce44SJohn Forte } 670*fcf3ce44SJohn Forte 671*fcf3ce44SJohn Forte return (rc); 672*fcf3ce44SJohn Forte } 673*fcf3ce44SJohn Forte 674*fcf3ce44SJohn Forte rdc_rc_t * 675*fcf3ce44SJohn Forte rdc_fsync(rdcconfig_t *rdc) 676*fcf3ce44SJohn Forte { 677*fcf3ce44SJohn Forte rdc_config_t *rdccfg; 678*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 679*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 680*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 681*fcf3ce44SJohn Forte rdc_rc_t *tmprc = NULL; 682*fcf3ce44SJohn Forte int trc; 683*fcf3ce44SJohn Forte 684*fcf3ce44SJohn Forte rdcp = rdc; 685*fcf3ce44SJohn Forte rc = new_rc(); 686*fcf3ce44SJohn Forte if (!rc) { 687*fcf3ce44SJohn Forte return (NULL); 688*fcf3ce44SJohn Forte } 689*fcf3ce44SJohn Forte rcp = rc; 690*fcf3ce44SJohn Forte 691*fcf3ce44SJohn Forte while (rdcp) { 692*fcf3ce44SJohn Forte /* freed in rdc_mtconfig */ 693*fcf3ce44SJohn Forte rdccfg = (rdc_config_t *)calloc(1, sizeof (rdc_config_t)); 694*fcf3ce44SJohn Forte rdccfg->rdc_set[0] = config2set(rdcp); 695*fcf3ce44SJohn Forte rdccfg->command = RDC_CMD_COPY; 696*fcf3ce44SJohn Forte rdccfg->options = RDC_OPT_FULL|RDC_OPT_FORWARD; 697*fcf3ce44SJohn Forte populate_addrs(&rdccfg->rdc_set[0], 0); 698*fcf3ce44SJohn Forte trc = thr_create(NULL, 0, rdc_mtconfig, 699*fcf3ce44SJohn Forte (void **) rdccfg, THR_BOUND, NULL); 700*fcf3ce44SJohn Forte rdcp = rdcp->next; 701*fcf3ce44SJohn Forte if (!rdcp) 702*fcf3ce44SJohn Forte break; 703*fcf3ce44SJohn Forte 704*fcf3ce44SJohn Forte } 705*fcf3ce44SJohn Forte 706*fcf3ce44SJohn Forte /* 707*fcf3ce44SJohn Forte * collect status here from thr_join-status, 708*fcf3ce44SJohn Forte * and add to rdc_rc_t chain ? 709*fcf3ce44SJohn Forte * this will block, but caller could always thread too 710*fcf3ce44SJohn Forte */ 711*fcf3ce44SJohn Forte while (thr_join(NULL, NULL, (void**) &tmprc) == 0) { 712*fcf3ce44SJohn Forte if (rc == NULL) { 713*fcf3ce44SJohn Forte rcp = rc = (rdc_rc_t *)tmprc; 714*fcf3ce44SJohn Forte } else { 715*fcf3ce44SJohn Forte rcp->next = (rdc_rc_t *)tmprc; 716*fcf3ce44SJohn Forte rcp = rcp->next; 717*fcf3ce44SJohn Forte } 718*fcf3ce44SJohn Forte } 719*fcf3ce44SJohn Forte 720*fcf3ce44SJohn Forte return (rc); 721*fcf3ce44SJohn Forte } 722*fcf3ce44SJohn Forte 723*fcf3ce44SJohn Forte rdc_rc_t * 724*fcf3ce44SJohn Forte rdc_rsync(rdcconfig_t *rdc) 725*fcf3ce44SJohn Forte { 726*fcf3ce44SJohn Forte rdc_config_t *rdccfg; 727*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 728*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 729*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 730*fcf3ce44SJohn Forte rdc_rc_t *tmprc = NULL; 731*fcf3ce44SJohn Forte int trc; 732*fcf3ce44SJohn Forte 733*fcf3ce44SJohn Forte rdcp = rdc; 734*fcf3ce44SJohn Forte rc = new_rc(); 735*fcf3ce44SJohn Forte if (!rc) { 736*fcf3ce44SJohn Forte return (NULL); 737*fcf3ce44SJohn Forte } 738*fcf3ce44SJohn Forte rcp = rc; 739*fcf3ce44SJohn Forte 740*fcf3ce44SJohn Forte while (rdcp) { 741*fcf3ce44SJohn Forte tmprc = cant_rsync(rdcp); 742*fcf3ce44SJohn Forte if (tmprc != NULL) { 743*fcf3ce44SJohn Forte if (rc == NULL) { 744*fcf3ce44SJohn Forte rcp = rc = tmprc; 745*fcf3ce44SJohn Forte } else { 746*fcf3ce44SJohn Forte rcp->next = tmprc; 747*fcf3ce44SJohn Forte rcp = rcp->next; 748*fcf3ce44SJohn Forte } 749*fcf3ce44SJohn Forte goto next; 750*fcf3ce44SJohn Forte } 751*fcf3ce44SJohn Forte 752*fcf3ce44SJohn Forte /* freed in rdc_mtconfig */ 753*fcf3ce44SJohn Forte rdccfg = (rdc_config_t *)calloc(1, sizeof (rdc_config_t)); 754*fcf3ce44SJohn Forte rdccfg->rdc_set[0] = config2set(rdcp); 755*fcf3ce44SJohn Forte rdccfg->command = RDC_CMD_COPY; 756*fcf3ce44SJohn Forte rdccfg->options = RDC_OPT_REVERSE|RDC_OPT_FULL; 757*fcf3ce44SJohn Forte populate_addrs(&rdccfg->rdc_set[0], 0); 758*fcf3ce44SJohn Forte trc = thr_create(NULL, 0, rdc_mtconfig, 759*fcf3ce44SJohn Forte (void **) rdccfg, THR_BOUND, NULL); 760*fcf3ce44SJohn Forte next: 761*fcf3ce44SJohn Forte rdcp = rdcp->next; 762*fcf3ce44SJohn Forte if (!rdcp) 763*fcf3ce44SJohn Forte break; 764*fcf3ce44SJohn Forte } 765*fcf3ce44SJohn Forte 766*fcf3ce44SJohn Forte /* 767*fcf3ce44SJohn Forte * collect status here from thr_join-status, 768*fcf3ce44SJohn Forte * and add to rdc_rc_t chain ? 769*fcf3ce44SJohn Forte * this will block, but caller could always thread too 770*fcf3ce44SJohn Forte */ 771*fcf3ce44SJohn Forte while (thr_join(NULL, NULL, (void**) &tmprc) == 0) { 772*fcf3ce44SJohn Forte if (rc == NULL) { 773*fcf3ce44SJohn Forte rcp = rc = (rdc_rc_t *)tmprc; 774*fcf3ce44SJohn Forte } else { 775*fcf3ce44SJohn Forte rcp->next = (rdc_rc_t *)tmprc; 776*fcf3ce44SJohn Forte rcp = rcp->next; 777*fcf3ce44SJohn Forte } 778*fcf3ce44SJohn Forte } 779*fcf3ce44SJohn Forte 780*fcf3ce44SJohn Forte return (rc); 781*fcf3ce44SJohn Forte } 782*fcf3ce44SJohn Forte 783*fcf3ce44SJohn Forte rdc_rc_t * 784*fcf3ce44SJohn Forte rdc_ursync(rdcconfig_t *rdc) 785*fcf3ce44SJohn Forte { 786*fcf3ce44SJohn Forte rdc_config_t *rdccfg; 787*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 788*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 789*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 790*fcf3ce44SJohn Forte rdc_rc_t *tmprc = NULL; 791*fcf3ce44SJohn Forte int trc; 792*fcf3ce44SJohn Forte 793*fcf3ce44SJohn Forte rdcp = rdc; 794*fcf3ce44SJohn Forte 795*fcf3ce44SJohn Forte while (rdcp) { 796*fcf3ce44SJohn Forte tmprc = cant_rsync(rdcp); 797*fcf3ce44SJohn Forte if (tmprc != NULL) { 798*fcf3ce44SJohn Forte if (rc == NULL) { 799*fcf3ce44SJohn Forte rcp = rc = tmprc; 800*fcf3ce44SJohn Forte } else { 801*fcf3ce44SJohn Forte rcp->next = tmprc; 802*fcf3ce44SJohn Forte rcp = rcp->next; 803*fcf3ce44SJohn Forte } 804*fcf3ce44SJohn Forte goto next; 805*fcf3ce44SJohn Forte } 806*fcf3ce44SJohn Forte 807*fcf3ce44SJohn Forte /* freed in rdc_mtconfig */ 808*fcf3ce44SJohn Forte rdccfg = (rdc_config_t *)calloc(1, sizeof (rdc_config_t)); 809*fcf3ce44SJohn Forte rdccfg->rdc_set[0] = config2set(rdcp); 810*fcf3ce44SJohn Forte rdccfg->command = RDC_CMD_COPY; 811*fcf3ce44SJohn Forte rdccfg->options = RDC_OPT_REVERSE | RDC_OPT_UPDATE; 812*fcf3ce44SJohn Forte populate_addrs(&rdccfg->rdc_set[0], 0); 813*fcf3ce44SJohn Forte trc = thr_create(NULL, 0, rdc_mtconfig, 814*fcf3ce44SJohn Forte (void **) rdccfg, THR_BOUND, NULL); 815*fcf3ce44SJohn Forte next: 816*fcf3ce44SJohn Forte rdcp = rdcp->next; 817*fcf3ce44SJohn Forte if (!rdcp) 818*fcf3ce44SJohn Forte break; 819*fcf3ce44SJohn Forte 820*fcf3ce44SJohn Forte } 821*fcf3ce44SJohn Forte 822*fcf3ce44SJohn Forte /* 823*fcf3ce44SJohn Forte * collect status here from thr_join-status, 824*fcf3ce44SJohn Forte * and add to rdc_rc_t chain ? 825*fcf3ce44SJohn Forte * this will block, but caller could always thread too 826*fcf3ce44SJohn Forte */ 827*fcf3ce44SJohn Forte while (thr_join(NULL, NULL, (void**) &tmprc) == 0) { 828*fcf3ce44SJohn Forte if (rc == NULL) { 829*fcf3ce44SJohn Forte rcp = rc = (rdc_rc_t *)tmprc; 830*fcf3ce44SJohn Forte } else { 831*fcf3ce44SJohn Forte rcp->next = (rdc_rc_t *)tmprc; 832*fcf3ce44SJohn Forte rcp = rcp->next; 833*fcf3ce44SJohn Forte } 834*fcf3ce44SJohn Forte } 835*fcf3ce44SJohn Forte 836*fcf3ce44SJohn Forte return (rc); 837*fcf3ce44SJohn Forte } 838*fcf3ce44SJohn Forte 839*fcf3ce44SJohn Forte rdc_rc_t * 840*fcf3ce44SJohn Forte rdc_wait(rdcconfig_t *rdc) 841*fcf3ce44SJohn Forte { 842*fcf3ce44SJohn Forte rdc_config_t rdccfg; 843*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 844*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 845*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 846*fcf3ce44SJohn Forte 847*fcf3ce44SJohn Forte rdcp = rdc; 848*fcf3ce44SJohn Forte rc = new_rc(); 849*fcf3ce44SJohn Forte if (!rc) { 850*fcf3ce44SJohn Forte return (NULL); 851*fcf3ce44SJohn Forte } 852*fcf3ce44SJohn Forte rcp = rc; 853*fcf3ce44SJohn Forte 854*fcf3ce44SJohn Forte while (rdcp) { 855*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 856*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdcp); 857*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_WAIT; 858*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 859*fcf3ce44SJohn Forte 860*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 861*fcf3ce44SJohn Forte 862*fcf3ce44SJohn Forte rdcp = rdcp->next; 863*fcf3ce44SJohn Forte if (!rdcp) 864*fcf3ce44SJohn Forte break; 865*fcf3ce44SJohn Forte 866*fcf3ce44SJohn Forte rcp->next = new_rc(); 867*fcf3ce44SJohn Forte rcp = rcp->next; 868*fcf3ce44SJohn Forte if (!rcp) 869*fcf3ce44SJohn Forte break; 870*fcf3ce44SJohn Forte } 871*fcf3ce44SJohn Forte return (rc); 872*fcf3ce44SJohn Forte } 873*fcf3ce44SJohn Forte 874*fcf3ce44SJohn Forte rdc_rc_t * 875*fcf3ce44SJohn Forte rdc_set_autosync(rdcconfig_t *rdc, int autosync) 876*fcf3ce44SJohn Forte { 877*fcf3ce44SJohn Forte rdc_config_t rdccfg; 878*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 879*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 880*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 881*fcf3ce44SJohn Forte 882*fcf3ce44SJohn Forte rdcp = rdc; 883*fcf3ce44SJohn Forte rc = new_rc(); 884*fcf3ce44SJohn Forte if (!rc) { 885*fcf3ce44SJohn Forte return (NULL); 886*fcf3ce44SJohn Forte } 887*fcf3ce44SJohn Forte rcp = rc; 888*fcf3ce44SJohn Forte 889*fcf3ce44SJohn Forte while (rdcp) { 890*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 891*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdcp); 892*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_TUNABLE; 893*fcf3ce44SJohn Forte rdccfg.rdc_set[0].autosync = autosync; 894*fcf3ce44SJohn Forte rdccfg.rdc_set[0].maxqitems = -1; 895*fcf3ce44SJohn Forte rdccfg.rdc_set[0].maxqfbas = -1; 896*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 897*fcf3ce44SJohn Forte 898*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 899*fcf3ce44SJohn Forte 900*fcf3ce44SJohn Forte rdcp = rdcp->next; 901*fcf3ce44SJohn Forte if (!rdcp) 902*fcf3ce44SJohn Forte break; 903*fcf3ce44SJohn Forte 904*fcf3ce44SJohn Forte rcp->next = new_rc(); 905*fcf3ce44SJohn Forte rcp = rcp->next; 906*fcf3ce44SJohn Forte if (!rcp) 907*fcf3ce44SJohn Forte break; 908*fcf3ce44SJohn Forte } 909*fcf3ce44SJohn Forte return (rc); 910*fcf3ce44SJohn Forte } 911*fcf3ce44SJohn Forte 912*fcf3ce44SJohn Forte rdc_rc_t * 913*fcf3ce44SJohn Forte rdc_set_maxqfbas(rdcconfig_t *rdc, int maxqfbas) 914*fcf3ce44SJohn Forte { 915*fcf3ce44SJohn Forte rdc_config_t rdccfg; 916*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 917*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 918*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 919*fcf3ce44SJohn Forte 920*fcf3ce44SJohn Forte rdcp = rdc; 921*fcf3ce44SJohn Forte rc = new_rc(); 922*fcf3ce44SJohn Forte if (!rc) { 923*fcf3ce44SJohn Forte return (NULL); 924*fcf3ce44SJohn Forte } 925*fcf3ce44SJohn Forte rcp = rc; 926*fcf3ce44SJohn Forte 927*fcf3ce44SJohn Forte while (rdcp) { 928*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 929*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdcp); 930*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_TUNABLE; 931*fcf3ce44SJohn Forte rdccfg.rdc_set[0].autosync = -1; 932*fcf3ce44SJohn Forte rdccfg.rdc_set[0].maxqitems = -1; 933*fcf3ce44SJohn Forte rdccfg.rdc_set[0].maxqfbas = maxqfbas; 934*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 935*fcf3ce44SJohn Forte 936*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 937*fcf3ce44SJohn Forte 938*fcf3ce44SJohn Forte rdcp = rdcp->next; 939*fcf3ce44SJohn Forte if (!rdcp) 940*fcf3ce44SJohn Forte break; 941*fcf3ce44SJohn Forte 942*fcf3ce44SJohn Forte rcp->next = new_rc(); 943*fcf3ce44SJohn Forte rcp = rcp->next; 944*fcf3ce44SJohn Forte if (!rcp) 945*fcf3ce44SJohn Forte break; 946*fcf3ce44SJohn Forte } 947*fcf3ce44SJohn Forte return (rc); 948*fcf3ce44SJohn Forte } 949*fcf3ce44SJohn Forte 950*fcf3ce44SJohn Forte rdc_rc_t * 951*fcf3ce44SJohn Forte rdc_set_maxqitems(rdcconfig_t *rdc, int maxqitems) 952*fcf3ce44SJohn Forte { 953*fcf3ce44SJohn Forte rdc_config_t rdccfg; 954*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 955*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 956*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 957*fcf3ce44SJohn Forte 958*fcf3ce44SJohn Forte rdcp = rdc; 959*fcf3ce44SJohn Forte rc = new_rc(); 960*fcf3ce44SJohn Forte 961*fcf3ce44SJohn Forte if (!rc) { 962*fcf3ce44SJohn Forte return (NULL); 963*fcf3ce44SJohn Forte } 964*fcf3ce44SJohn Forte rcp = rc; 965*fcf3ce44SJohn Forte 966*fcf3ce44SJohn Forte while (rdcp) { 967*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 968*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdc); 969*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_TUNABLE; 970*fcf3ce44SJohn Forte rdccfg.rdc_set[0].autosync = -1; 971*fcf3ce44SJohn Forte rdccfg.rdc_set[0].maxqitems = maxqitems; 972*fcf3ce44SJohn Forte rdccfg.rdc_set[0].maxqfbas = -1; 973*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 974*fcf3ce44SJohn Forte 975*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 976*fcf3ce44SJohn Forte 977*fcf3ce44SJohn Forte rdcp = rdcp->next; 978*fcf3ce44SJohn Forte if (!rdcp) 979*fcf3ce44SJohn Forte break; 980*fcf3ce44SJohn Forte 981*fcf3ce44SJohn Forte rcp->next = new_rc(); 982*fcf3ce44SJohn Forte rcp = rcp->next; 983*fcf3ce44SJohn Forte if (!rcp) 984*fcf3ce44SJohn Forte break; 985*fcf3ce44SJohn Forte } 986*fcf3ce44SJohn Forte return (rc); 987*fcf3ce44SJohn Forte } 988*fcf3ce44SJohn Forte 989*fcf3ce44SJohn Forte rdc_set_t 990*fcf3ce44SJohn Forte rdc_status(rdcconfig_t *rdc) 991*fcf3ce44SJohn Forte { 992*fcf3ce44SJohn Forte rdc_config_t rdccfg; 993*fcf3ce44SJohn Forte 994*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 995*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdc); 996*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_STATUS; 997*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 998*fcf3ce44SJohn Forte rdc_config(&rdccfg); 999*fcf3ce44SJohn Forte 1000*fcf3ce44SJohn Forte return (rdccfg.rdc_set[0]); 1001*fcf3ce44SJohn Forte } 1002*fcf3ce44SJohn Forte 1003*fcf3ce44SJohn Forte int 1004*fcf3ce44SJohn Forte rdc_get_autosync(rdcconfig_t *rdc) 1005*fcf3ce44SJohn Forte { 1006*fcf3ce44SJohn Forte rdc_set_t rdcset; 1007*fcf3ce44SJohn Forte 1008*fcf3ce44SJohn Forte rdcset = rdc_status(rdc); 1009*fcf3ce44SJohn Forte return (rdcset.autosync); 1010*fcf3ce44SJohn Forte } 1011*fcf3ce44SJohn Forte 1012*fcf3ce44SJohn Forte int 1013*fcf3ce44SJohn Forte rdc_get_maxqfbas(rdcconfig_t *rdc) 1014*fcf3ce44SJohn Forte { 1015*fcf3ce44SJohn Forte rdc_set_t rdcset; 1016*fcf3ce44SJohn Forte 1017*fcf3ce44SJohn Forte rdcset = rdc_status(rdc); 1018*fcf3ce44SJohn Forte return (rdcset.maxqfbas); 1019*fcf3ce44SJohn Forte 1020*fcf3ce44SJohn Forte } 1021*fcf3ce44SJohn Forte 1022*fcf3ce44SJohn Forte int 1023*fcf3ce44SJohn Forte rdc_get_maxqitems(rdcconfig_t *rdc) 1024*fcf3ce44SJohn Forte { 1025*fcf3ce44SJohn Forte rdc_set_t rdcset; 1026*fcf3ce44SJohn Forte 1027*fcf3ce44SJohn Forte rdcset = rdc_status(rdc); 1028*fcf3ce44SJohn Forte return (rdcset.maxqitems); 1029*fcf3ce44SJohn Forte 1030*fcf3ce44SJohn Forte } 1031*fcf3ce44SJohn Forte 1032*fcf3ce44SJohn Forte int 1033*fcf3ce44SJohn Forte set_mode(rdcconfig_t *rdc) 1034*fcf3ce44SJohn Forte { 1035*fcf3ce44SJohn Forte if (strcmp(rdc->mode, "async") == 0) 1036*fcf3ce44SJohn Forte return (RDC_OPT_ASYNC); 1037*fcf3ce44SJohn Forte else 1038*fcf3ce44SJohn Forte return (RDC_OPT_SYNC); 1039*fcf3ce44SJohn Forte } 1040*fcf3ce44SJohn Forte 1041*fcf3ce44SJohn Forte /* 1042*fcf3ce44SJohn Forte * reconfig bitmaps are single set only ops 1043*fcf3ce44SJohn Forte * for obvious reasons 1044*fcf3ce44SJohn Forte */ 1045*fcf3ce44SJohn Forte rdc_rc_t * 1046*fcf3ce44SJohn Forte rdc_reconfig_pbmp(rdcconfig_t *rdc, char *pbmp) 1047*fcf3ce44SJohn Forte { 1048*fcf3ce44SJohn Forte rdc_config_t rdccfg; 1049*fcf3ce44SJohn Forte rdc_rc_t *rc; 1050*fcf3ce44SJohn Forte 1051*fcf3ce44SJohn Forte rc = new_rc(); 1052*fcf3ce44SJohn Forte if ((!rc) || (!pbmp)) 1053*fcf3ce44SJohn Forte return (NULL); 1054*fcf3ce44SJohn Forte 1055*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 1056*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdc); 1057*fcf3ce44SJohn Forte strncpy(rdccfg.rdc_set[0].primary.bitmap, pbmp, NSC_MAXPATH); 1058*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_RECONFIG; 1059*fcf3ce44SJohn Forte rdccfg.options |= set_mode(rdc); 1060*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 1061*fcf3ce44SJohn Forte 1062*fcf3ce44SJohn Forte if (can_reconfig_pbmp(rdc, pbmp)) 1063*fcf3ce44SJohn Forte *rc = rdc_config(&rdccfg); 1064*fcf3ce44SJohn Forte else 1065*fcf3ce44SJohn Forte populate_rc(rc, rdc); 1066*fcf3ce44SJohn Forte 1067*fcf3ce44SJohn Forte if ((rc->rc == 0) && (rdc->persist)) 1068*fcf3ce44SJohn Forte if (replace_cfgfield(rdc, "pbitmap", pbmp) < 0) { 1069*fcf3ce44SJohn Forte rc->rc = -1; 1070*fcf3ce44SJohn Forte strncpy(rc->msg, rdc_error(NULL), RDC_ERR_SIZE); 1071*fcf3ce44SJohn Forte } 1072*fcf3ce44SJohn Forte return (rc); 1073*fcf3ce44SJohn Forte } 1074*fcf3ce44SJohn Forte 1075*fcf3ce44SJohn Forte rdc_rc_t * 1076*fcf3ce44SJohn Forte rdc_reconfig_sbmp(rdcconfig_t *rdc, char *sbmp) 1077*fcf3ce44SJohn Forte { 1078*fcf3ce44SJohn Forte rdc_config_t rdccfg; 1079*fcf3ce44SJohn Forte rdc_rc_t *rc; 1080*fcf3ce44SJohn Forte 1081*fcf3ce44SJohn Forte rc = new_rc(); 1082*fcf3ce44SJohn Forte if (!rc) 1083*fcf3ce44SJohn Forte return (NULL); 1084*fcf3ce44SJohn Forte 1085*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 1086*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdc); 1087*fcf3ce44SJohn Forte strncpy(rdccfg.rdc_set[0].secondary.bitmap, sbmp, NSC_MAXPATH); 1088*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_RECONFIG; 1089*fcf3ce44SJohn Forte rdccfg.options |= set_mode(rdc); 1090*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 1091*fcf3ce44SJohn Forte 1092*fcf3ce44SJohn Forte if (can_reconfig_sbmp(rdc, sbmp)) 1093*fcf3ce44SJohn Forte *rc = rdc_config(&rdccfg); 1094*fcf3ce44SJohn Forte else 1095*fcf3ce44SJohn Forte populate_rc(rc, rdc); 1096*fcf3ce44SJohn Forte 1097*fcf3ce44SJohn Forte if ((rc->rc == 0) && (rdc->persist)) 1098*fcf3ce44SJohn Forte replace_cfgfield(rdc, "sbitmap", sbmp); 1099*fcf3ce44SJohn Forte 1100*fcf3ce44SJohn Forte return (rc); 1101*fcf3ce44SJohn Forte } 1102*fcf3ce44SJohn Forte 1103*fcf3ce44SJohn Forte rdc_rc_t * 1104*fcf3ce44SJohn Forte rdc_reconfig_group(rdcconfig_t *rdc, char *group) 1105*fcf3ce44SJohn Forte { 1106*fcf3ce44SJohn Forte rdc_config_t rdccfg; 1107*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 1108*fcf3ce44SJohn Forte rdcconfig_t *cfg_rdcs = NULL; 1109*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 1110*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 1111*fcf3ce44SJohn Forte 1112*fcf3ce44SJohn Forte rdcp = rdc; 1113*fcf3ce44SJohn Forte rc = new_rc(); 1114*fcf3ce44SJohn Forte if (!rc) { 1115*fcf3ce44SJohn Forte return (NULL); 1116*fcf3ce44SJohn Forte } 1117*fcf3ce44SJohn Forte rcp = rc; 1118*fcf3ce44SJohn Forte 1119*fcf3ce44SJohn Forte while (rdcp) { 1120*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 1121*fcf3ce44SJohn Forte /* just in case */ 1122*fcf3ce44SJohn Forte strncpy(rdcp->group, group, NSC_MAXPATH); 1123*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdcp); 1124*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_RECONFIG; 1125*fcf3ce44SJohn Forte rdccfg.options |= set_mode(rdcp); 1126*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 1127*fcf3ce44SJohn Forte 1128*fcf3ce44SJohn Forte /* reconfig group rules enforced in kernel */ 1129*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 1130*fcf3ce44SJohn Forte 1131*fcf3ce44SJohn Forte rdcp = rdcp->next; 1132*fcf3ce44SJohn Forte if (!rdcp) 1133*fcf3ce44SJohn Forte break; 1134*fcf3ce44SJohn Forte 1135*fcf3ce44SJohn Forte rcp->next = new_rc(); 1136*fcf3ce44SJohn Forte rcp = rcp->next; 1137*fcf3ce44SJohn Forte if (!rcp) 1138*fcf3ce44SJohn Forte break; 1139*fcf3ce44SJohn Forte } 1140*fcf3ce44SJohn Forte rcp = rc; 1141*fcf3ce44SJohn Forte rdcp = rdc; 1142*fcf3ce44SJohn Forte cfg_rdcs = chain_successful(rdcp, rcp); 1143*fcf3ce44SJohn Forte replace_cfgfield(cfg_rdcs, "group", group); 1144*fcf3ce44SJohn Forte rdc_free_config(cfg_rdcs, RDC_FREEALL); 1145*fcf3ce44SJohn Forte 1146*fcf3ce44SJohn Forte return (rc); 1147*fcf3ce44SJohn Forte } 1148*fcf3ce44SJohn Forte /*ARGSUSED*/ 1149*fcf3ce44SJohn Forte rdc_rc_t * 1150*fcf3ce44SJohn Forte rdc_reconfig_ctag(rdcconfig_t *rdc, char *ctag) 1151*fcf3ce44SJohn Forte { 1152*fcf3ce44SJohn Forte return (NULL); 1153*fcf3ce44SJohn Forte } 1154*fcf3ce44SJohn Forte 1155*fcf3ce44SJohn Forte rdc_rc_t * 1156*fcf3ce44SJohn Forte rdc_set_sync(rdcconfig_t *rdc) 1157*fcf3ce44SJohn Forte { 1158*fcf3ce44SJohn Forte rdc_config_t rdccfg; 1159*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 1160*fcf3ce44SJohn Forte rdcconfig_t *cfg_rdcs = NULL; 1161*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 1162*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 1163*fcf3ce44SJohn Forte 1164*fcf3ce44SJohn Forte rdcp = rdc; 1165*fcf3ce44SJohn Forte rc = new_rc(); 1166*fcf3ce44SJohn Forte if (!rc) { 1167*fcf3ce44SJohn Forte return (NULL); 1168*fcf3ce44SJohn Forte } 1169*fcf3ce44SJohn Forte rcp = rc; 1170*fcf3ce44SJohn Forte 1171*fcf3ce44SJohn Forte while (rdcp) { 1172*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 1173*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdc); 1174*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_RECONFIG; 1175*fcf3ce44SJohn Forte rdccfg.options |= RDC_OPT_SYNC; 1176*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 1177*fcf3ce44SJohn Forte 1178*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 1179*fcf3ce44SJohn Forte 1180*fcf3ce44SJohn Forte rdcp = rdcp->next; 1181*fcf3ce44SJohn Forte if (!rdcp) 1182*fcf3ce44SJohn Forte break; 1183*fcf3ce44SJohn Forte 1184*fcf3ce44SJohn Forte rcp->next = new_rc(); 1185*fcf3ce44SJohn Forte rcp = rcp->next; 1186*fcf3ce44SJohn Forte if (!rcp) 1187*fcf3ce44SJohn Forte break; 1188*fcf3ce44SJohn Forte } 1189*fcf3ce44SJohn Forte 1190*fcf3ce44SJohn Forte rcp = rc; 1191*fcf3ce44SJohn Forte rdcp = rdc; 1192*fcf3ce44SJohn Forte cfg_rdcs = chain_successful(rdcp, rcp); 1193*fcf3ce44SJohn Forte replace_cfgfield(cfg_rdcs, "mode", "sync"); 1194*fcf3ce44SJohn Forte rdc_free_config(cfg_rdcs, RDC_FREEALL); 1195*fcf3ce44SJohn Forte 1196*fcf3ce44SJohn Forte return (rc); 1197*fcf3ce44SJohn Forte } 1198*fcf3ce44SJohn Forte 1199*fcf3ce44SJohn Forte rdc_rc_t * 1200*fcf3ce44SJohn Forte rdc_set_async(rdcconfig_t *rdc) 1201*fcf3ce44SJohn Forte { 1202*fcf3ce44SJohn Forte rdc_config_t rdccfg; 1203*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 1204*fcf3ce44SJohn Forte rdcconfig_t *cfg_rdcs = NULL; 1205*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 1206*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 1207*fcf3ce44SJohn Forte 1208*fcf3ce44SJohn Forte rdcp = rdc; 1209*fcf3ce44SJohn Forte rc = new_rc(); 1210*fcf3ce44SJohn Forte if (!rc) { 1211*fcf3ce44SJohn Forte return (NULL); 1212*fcf3ce44SJohn Forte } 1213*fcf3ce44SJohn Forte rcp = rc; 1214*fcf3ce44SJohn Forte 1215*fcf3ce44SJohn Forte while (rdcp) { 1216*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 1217*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdcp); 1218*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_RECONFIG; 1219*fcf3ce44SJohn Forte rdccfg.options |= RDC_OPT_ASYNC; 1220*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 1221*fcf3ce44SJohn Forte 1222*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 1223*fcf3ce44SJohn Forte 1224*fcf3ce44SJohn Forte rdcp = rdcp->next; 1225*fcf3ce44SJohn Forte if (!rdcp) 1226*fcf3ce44SJohn Forte break; 1227*fcf3ce44SJohn Forte 1228*fcf3ce44SJohn Forte rcp->next = new_rc(); 1229*fcf3ce44SJohn Forte rcp = rcp->next; 1230*fcf3ce44SJohn Forte if (!rcp) 1231*fcf3ce44SJohn Forte break; 1232*fcf3ce44SJohn Forte } 1233*fcf3ce44SJohn Forte rcp = rc; 1234*fcf3ce44SJohn Forte rdcp = rdc; 1235*fcf3ce44SJohn Forte cfg_rdcs = chain_successful(rdcp, rcp); 1236*fcf3ce44SJohn Forte replace_cfgfield(cfg_rdcs, "mode", "async"); 1237*fcf3ce44SJohn Forte rdc_free_config(cfg_rdcs, RDC_FREEALL); 1238*fcf3ce44SJohn Forte 1239*fcf3ce44SJohn Forte return (rc); 1240*fcf3ce44SJohn Forte } 1241*fcf3ce44SJohn Forte 1242*fcf3ce44SJohn Forte rdc_rc_t * 1243*fcf3ce44SJohn Forte rdc_health(rdcconfig_t *rdc) 1244*fcf3ce44SJohn Forte { 1245*fcf3ce44SJohn Forte rdc_config_t rdccfg; 1246*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 1247*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 1248*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 1249*fcf3ce44SJohn Forte 1250*fcf3ce44SJohn Forte rdcp = rdc; 1251*fcf3ce44SJohn Forte rc = new_rc(); 1252*fcf3ce44SJohn Forte if (!rc) { 1253*fcf3ce44SJohn Forte return (NULL); 1254*fcf3ce44SJohn Forte } 1255*fcf3ce44SJohn Forte rcp = rc; 1256*fcf3ce44SJohn Forte 1257*fcf3ce44SJohn Forte while (rdcp) { 1258*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 1259*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdcp); 1260*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_HEALTH; 1261*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 1262*fcf3ce44SJohn Forte 1263*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 1264*fcf3ce44SJohn Forte 1265*fcf3ce44SJohn Forte rdcp = rdcp->next; 1266*fcf3ce44SJohn Forte if (!rdcp) 1267*fcf3ce44SJohn Forte break; 1268*fcf3ce44SJohn Forte 1269*fcf3ce44SJohn Forte rcp->next = new_rc(); 1270*fcf3ce44SJohn Forte rcp = rcp->next; 1271*fcf3ce44SJohn Forte 1272*fcf3ce44SJohn Forte if (!rcp) 1273*fcf3ce44SJohn Forte break; 1274*fcf3ce44SJohn Forte 1275*fcf3ce44SJohn Forte } 1276*fcf3ce44SJohn Forte return (rc); 1277*fcf3ce44SJohn Forte } 1278*fcf3ce44SJohn Forte 1279*fcf3ce44SJohn Forte rdc_rc_t * 1280*fcf3ce44SJohn Forte rdc_reverse_role(rdcconfig_t *rdc) 1281*fcf3ce44SJohn Forte { 1282*fcf3ce44SJohn Forte rdc_config_t rdccfg; 1283*fcf3ce44SJohn Forte rdcconfig_t *rdcp = NULL; 1284*fcf3ce44SJohn Forte rdcconfig_t *cfg_rdcs = NULL; 1285*fcf3ce44SJohn Forte rdc_rc_t *rc = NULL; 1286*fcf3ce44SJohn Forte rdc_rc_t *rcp = NULL; 1287*fcf3ce44SJohn Forte 1288*fcf3ce44SJohn Forte rdcp = rdc; 1289*fcf3ce44SJohn Forte rc = new_rc(); 1290*fcf3ce44SJohn Forte if (!rc) { 1291*fcf3ce44SJohn Forte return (NULL); 1292*fcf3ce44SJohn Forte } 1293*fcf3ce44SJohn Forte rcp = rc; 1294*fcf3ce44SJohn Forte 1295*fcf3ce44SJohn Forte while (rdcp) { 1296*fcf3ce44SJohn Forte bzero(&rdccfg, sizeof (rdc_config_t)); 1297*fcf3ce44SJohn Forte rdccfg.rdc_set[0] = config2set(rdcp); 1298*fcf3ce44SJohn Forte rdccfg.command = RDC_CMD_RECONFIG; 1299*fcf3ce44SJohn Forte rdccfg.options |= RDC_OPT_REVERSE_ROLE; 1300*fcf3ce44SJohn Forte rdccfg.options |= set_mode(rdcp); 1301*fcf3ce44SJohn Forte populate_addrs(&rdccfg.rdc_set[0], 0); 1302*fcf3ce44SJohn Forte 1303*fcf3ce44SJohn Forte *rcp = rdc_config(&rdccfg); 1304*fcf3ce44SJohn Forte 1305*fcf3ce44SJohn Forte rdcp = rdcp->next; 1306*fcf3ce44SJohn Forte if (!rdcp) 1307*fcf3ce44SJohn Forte break; 1308*fcf3ce44SJohn Forte 1309*fcf3ce44SJohn Forte rcp->next = new_rc(); 1310*fcf3ce44SJohn Forte rcp = rcp->next; 1311*fcf3ce44SJohn Forte if (!rcp) 1312*fcf3ce44SJohn Forte break; 1313*fcf3ce44SJohn Forte } 1314*fcf3ce44SJohn Forte rcp = rc; 1315*fcf3ce44SJohn Forte rdcp = rdc; 1316*fcf3ce44SJohn Forte cfg_rdcs = chain_successful(rdcp, rcp); 1317*fcf3ce44SJohn Forte reverse_in_cfg(cfg_rdcs); 1318*fcf3ce44SJohn Forte rdc_free_config(cfg_rdcs, RDC_FREEALL); 1319*fcf3ce44SJohn Forte 1320*fcf3ce44SJohn Forte return (rc); 1321*fcf3ce44SJohn Forte } 1322