bug 8115: Source IP filtering in Virtual Router

Passing the additional source cidrs paramter to the xapi.
This commit is contained in:
Abhinandan Prateek 2011-05-12 13:37:43 +05:30
parent 1929c6bb2b
commit d752a94838
9 changed files with 78 additions and 22 deletions

View File

@ -17,8 +17,11 @@
*/
package com.cloud.agent.api.to;
import java.util.List;
import com.cloud.network.rules.FirewallRule;
import com.cloud.network.rules.PortForwardingRule;
import com.cloud.utils.StringUtils;
import com.cloud.utils.net.NetUtils;
/**
@ -30,6 +33,7 @@ import com.cloud.utils.net.NetUtils;
public class PortForwardingRuleTO extends FirewallRuleTO {
String dstIp;
int[] dstPortRange;
List<String> sourceCidrs;
protected PortForwardingRuleTO() {
super();
@ -39,6 +43,7 @@ public class PortForwardingRuleTO extends FirewallRuleTO {
super(rule, srcIp);
this.dstIp = rule.getDestinationIpAddress().addr();
this.dstPortRange = new int[] { rule.getDestinationPortStart(), rule.getDestinationPortEnd() };
this.sourceCidrs = rule.getSourceCidrList();
}
protected PortForwardingRuleTO(long id, String srcIp, int srcPortStart, int srcPortEnd, String dstIp, int dstPortStart, int dstPortEnd, String protocol, boolean revoked, boolean brandNew) {
@ -58,4 +63,13 @@ public class PortForwardingRuleTO extends FirewallRuleTO {
public String getStringDstPortRange() {
return NetUtils.portRangeToString(dstPortRange);
}
public List<String> getSourceCidrs(){
return sourceCidrs;
}
public String geStringSourceCidrs(){
return sourceCidrs==null ? null : StringUtils.join(sourceCidrs, ",");
}
}

View File

@ -40,6 +40,7 @@ import com.cloud.network.rules.PortForwardingRule;
import com.cloud.user.Account;
import com.cloud.user.UserContext;
import com.cloud.utils.net.Ip;
import com.cloud.utils.net.NetUtils;
@Implementation(description = "Creates a port forwarding rule", responseObject = FirewallRuleResponse.class)
public class CreatePortForwardingRuleCmd extends BaseAsyncCreateCmd implements PortForwardingRule {
@ -108,20 +109,27 @@ public class CreatePortForwardingRuleCmd extends BaseAsyncCreateCmd implements P
public String getCommandName() {
return s_name;
}
@Override
public void setSourceCidrList(List<String> cidrs){
cidrlist = cidrs;
}
@Override
public void execute() throws ResourceUnavailableException {
UserContext callerContext = UserContext.current();
boolean success = false;
PortForwardingRule rule = _entityMgr.findById(PortForwardingRule.class, getEntityId());
// load cidrs if any
rule.setSourceCidrList(_rulesService.getSourceCidrs(rule.getId()));
try {
UserContext.current().setEventDetails("Rule Id: " + getEntityId());
success = _rulesService.applyPortForwardingRules(rule.getSourceIpAddressId(), callerContext.getCaller());
// State is different after the rule is applied, so get new object here
rule = _entityMgr.findById(PortForwardingRule.class, getEntityId());
FirewallRuleResponse fwResponse = new FirewallRuleResponse();
FirewallRuleResponse fwResponse = new FirewallRuleResponse();
if (rule != null) {
fwResponse = _responseGenerator.createFirewallRuleResponse(rule);
setResponseObject(fwResponse);
@ -210,6 +218,12 @@ public class CreatePortForwardingRuleCmd extends BaseAsyncCreateCmd implements P
@Override
public void create() {
if (cidrlist != null)
for (String cidr: cidrlist){
if (!NetUtils.isValidCIDR(cidr)){
throw new ServerApiException(BaseCmd.PARAM_ERROR, "Source cidrs formatting error " + cidr);
}
}
try {
PortForwardingRule result = _rulesService.createPortForwardingRule(this, virtualMachineId);
setEntityId(result.getId());

View File

@ -49,6 +49,8 @@ public interface PortForwardingRule extends FirewallRule {
* @return source cidr to forward
*/
List<String> getSourceCidrList();
/**
* @return source cidr to forward
*/
void setSourceCidrList(List<String> cidrs);
}

View File

@ -68,4 +68,6 @@ public interface RulesService {
StaticNatRule buildStaticNatRule(FirewallRule rule);
List<String> getSourceCidrs(long ruleId);
}

View File

@ -1207,18 +1207,22 @@ public abstract class CitrixResourceBase implements ServerResource, HypervisorRe
Connection conn = getConnection();
String routerIp = cmd.getAccessDetail(NetworkElementCommand.ROUTER_IP);
String args = routerIp;
String[] results = new String[cmd.getRules().length];
int i = 0;
for (PortForwardingRuleTO rule : cmd.getRules()) {
args += rule.revoked() ? " -D " : " -A ";
args += " -P " + rule.getProtocol().toLowerCase();
args += " -l " + rule.getSrcIp();
args += " -p " + rule.getStringSrcPortRange();
args += " -r " + rule.getDstIp();
args += " -d " + rule.getStringDstPortRange();
StringBuilder args = new StringBuilder();
args.append(routerIp);
args.append(rule.revoked() ? " -D " : " -A ");
args.append(" -P ").append(rule.getProtocol().toLowerCase());
args.append(" -l ").append(rule.getSrcIp());
args.append(" -p ").append(rule.getStringSrcPortRange());
args.append(" -r ").append(rule.getDstIp());
args.append(" -d ").append(rule.getStringDstPortRange());
if (rule.geStringSourceCidrs() != null){
args.append(" -s " + rule.geStringSourceCidrs());
}
String result = callHostPlugin(conn, "vmops", "setFirewallRule", "args", args.toString());
String result = callHostPlugin(conn, "vmops", "setFirewallRule", "args", args);
results[i++] = (result == null || result.isEmpty()) ? "Failed" : null;
}

View File

@ -73,6 +73,7 @@ import com.cloud.keystore.KeystoreManagerImpl;
import com.cloud.maint.UpgradeManagerImpl;
import com.cloud.maint.dao.AgentUpgradeDaoImpl;
import com.cloud.network.NetworkManagerImpl;
import com.cloud.network.dao.FirewallRulesCidrsDaoImpl;
import com.cloud.network.dao.FirewallRulesDaoImpl;
import com.cloud.network.dao.IPAddressDaoImpl;
import com.cloud.network.dao.LoadBalancerDaoImpl;
@ -256,6 +257,7 @@ public class DefaultComponentLibrary extends ComponentLibraryBase implements Com
addDao("ItWorkDao", ItWorkDaoImpl.class);
addDao("FirewallRulesDao", FirewallRulesDaoImpl.class);
addDao("PortForwardingRulesDao", PortForwardingRulesDaoImpl.class);
addDao("FirewallRulesCidrsDao", FirewallRulesCidrsDaoImpl.class);
addDao("SSHKeyPairDao", SSHKeyPairDaoImpl.class);
addDao("UsageEventDao", UsageEventDaoImpl.class);
addDao("ClusterDetailsDao", ClusterDetailsDaoImpl.class);

View File

@ -32,7 +32,7 @@ import com.cloud.utils.db.SearchCriteria;
import com.cloud.utils.db.Transaction;
@Local(value=FirewallRulesCidrsDaoImpl.class)
@Local(value=FirewallRulesCidrsDao.class)
public class FirewallRulesCidrsDaoImpl extends GenericDaoBase<FirewallRulesCidrsVO, Long> implements FirewallRulesCidrsDao {
private static final Logger s_logger = Logger.getLogger(FirewallRulesCidrsDaoImpl.class);
protected final SearchBuilder<FirewallRulesCidrsVO> CidrsSearch;
@ -49,12 +49,12 @@ public class FirewallRulesCidrsDaoImpl extends GenericDaoBase<FirewallRulesCidrs
sc.setParameters("firewallRuleId", firewallRuleId);
List<FirewallRulesCidrsVO> results = search(sc, null);
List<String> hostTags = new ArrayList<String>(results.size());
List<String> cidrs = new ArrayList<String>(results.size());
for (FirewallRulesCidrsVO result : results) {
hostTags.add(result.getCidr());
cidrs.add(result.getCidr());
}
return hostTags;
return cidrs;
}
@Override @DB
@ -63,7 +63,6 @@ public class FirewallRulesCidrsDaoImpl extends GenericDaoBase<FirewallRulesCidrs
txn.start();
for (String tag : sourceCidrs) {
s_logger.info("Saving cidrs " + tag);
FirewallRulesCidrsVO vo = new FirewallRulesCidrsVO(firewallRuleId, tag);
persist(vo);
}

View File

@ -46,6 +46,7 @@ import com.cloud.network.Network;
import com.cloud.network.Network.Capability;
import com.cloud.network.Network.Service;
import com.cloud.network.NetworkManager;
import com.cloud.network.dao.FirewallRulesCidrsDao;
import com.cloud.network.dao.FirewallRulesDao;
import com.cloud.network.dao.IPAddressDao;
import com.cloud.network.rules.FirewallRule.Purpose;
@ -80,6 +81,8 @@ public class RulesManagerImpl implements RulesManager, RulesService, Manager {
@Inject
PortForwardingRulesDao _forwardingDao;
@Inject
FirewallRulesCidrsDao _firewallCidrsDao;
@Inject
FirewallRulesDao _firewallDao;
@Inject
IPAddressDao _ipAddressDao;
@ -663,14 +666,26 @@ public class RulesManagerImpl implements RulesManager, RulesService, Manager {
return _forwardingDao.search(sc, filter);
}
@Override
public List<String> getSourceCidrs(long ruleId){
return _firewallCidrsDao.getSourceCidrs(ruleId);
}
@Override
public boolean applyPortForwardingRules(long ipId, boolean continueOnError, Account caller) {
List<PortForwardingRuleVO> rules = _forwardingDao.listForApplication(ipId);
if (rules.size() == 0) {
s_logger.debug("There are no firwall rules to apply for ip id=" + ipId);
return true;
}
for (PortForwardingRuleVO rule: rules){
// load cidrs if any
rule.setSourceCidrList(_firewallCidrsDao.getSourceCidrs(rule.getId()));
}
if (caller != null) {
_accountMgr.checkAccess(caller, rules.toArray(new PortForwardingRuleVO[rules.size()]));

View File

@ -37,9 +37,13 @@ public interface PortForwardingRulesDao extends GenericDao<PortForwardingRuleVO,
List<PortForwardingRuleVO> listByIp(long ipId);
List<PortForwardingRuleVO> listByVm(Long vmId);
List<PortForwardingRuleVO> listByNetwork(long networkId);
List<PortForwardingRuleVO> listByAccount(long accountId);
List<PortForwardingRuleVO> listByVm(Long vmId);
List<PortForwardingRuleVO> listByNetwork(long networkId);
List<PortForwardingRuleVO> listByAccount(long accountId);
void loadSourceCidrs(PortForwardingRuleVO portForwardingRule);
void saveSourceCidrs(PortForwardingRuleVO portForwardingRule);
}