Reset the specified master with sentinelResetMaster(), and also change * the ip:port address, but take the name of the instance unmodified. * * This is used to handle the +switch-master event. * * The function returns C_ERR if the address can't be resolved for some * reason. Otherwise C_OK is returned. */
| 1629 | * The function returns C_ERR if the address can't be resolved for some |
| 1630 | * reason. Otherwise C_OK is returned. */ |
| 1631 | int sentinelResetMasterAndChangeAddress(sentinelRedisInstance *master, char *hostname, int port) { |
| 1632 | sentinelAddr *oldaddr, *newaddr; |
| 1633 | sentinelAddr **slaves = NULL; |
| 1634 | int numslaves = 0, j; |
| 1635 | dictIterator *di; |
| 1636 | dictEntry *de; |
| 1637 | |
| 1638 | newaddr = createSentinelAddr(hostname,port); |
| 1639 | if (newaddr == NULL) return C_ERR; |
| 1640 | |
| 1641 | /* There can be only 0 or 1 slave that has the newaddr. |
| 1642 | * and It can add old master 1 more slave. |
| 1643 | * so It allocates dictSize(master->slaves) + 1 */ |
| 1644 | slaves = (sentinelAddr**)zmalloc(sizeof(sentinelAddr*)*(dictSize(master->slaves) + 1)); |
| 1645 | |
| 1646 | /* Don't include the one having the address we are switching to. */ |
| 1647 | di = dictGetIterator(master->slaves); |
| 1648 | while((de = dictNext(di)) != NULL) { |
| 1649 | sentinelRedisInstance *slave = (sentinelRedisInstance*)dictGetVal(de); |
| 1650 | |
| 1651 | if (sentinelAddrIsEqual(slave->addr,newaddr)) continue; |
| 1652 | slaves[numslaves++] = dupSentinelAddr(slave->addr); |
| 1653 | } |
| 1654 | dictReleaseIterator(di); |
| 1655 | |
| 1656 | /* If we are switching to a different address, include the old address |
| 1657 | * as a slave as well, so that we'll be able to sense / reconfigure |
| 1658 | * the old master. */ |
| 1659 | if (!sentinelAddrIsEqual(newaddr,master->addr)) { |
| 1660 | slaves[numslaves++] = dupSentinelAddr(master->addr); |
| 1661 | } |
| 1662 | |
| 1663 | /* Reset and switch address. */ |
| 1664 | sentinelResetMaster(master,SENTINEL_RESET_NO_SENTINELS); |
| 1665 | oldaddr = master->addr; |
| 1666 | master->addr = newaddr; |
| 1667 | master->o_down_since_time = 0; |
| 1668 | master->s_down_since_time = 0; |
| 1669 | |
| 1670 | /* Add slaves back. */ |
| 1671 | for (j = 0; j < numslaves; j++) { |
| 1672 | sentinelRedisInstance *slave; |
| 1673 | |
| 1674 | slave = createSentinelRedisInstance(NULL,SRI_SLAVE,slaves[j]->hostname, |
| 1675 | slaves[j]->port, master->quorum, master); |
| 1676 | releaseSentinelAddr(slaves[j]); |
| 1677 | if (slave) sentinelEvent(LL_NOTICE,"+slave",slave,"%@"); |
| 1678 | } |
| 1679 | zfree(slaves); |
| 1680 | |
| 1681 | /* Release the old address at the end so we are safe even if the function |
| 1682 | * gets the master->addr->ip and master->addr->port as arguments. */ |
| 1683 | releaseSentinelAddr(oldaddr); |
| 1684 | sentinelFlushConfig(); |
| 1685 | return C_OK; |
| 1686 | } |
| 1687 | |
| 1688 | /* Return non-zero if there was no SDOWN or ODOWN error associated to this |
no test coverage detected