summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorHans-Joerg Hoexer <hshoexer@cvs.openbsd.org>2006-04-13 11:55:08 +0000
committerHans-Joerg Hoexer <hshoexer@cvs.openbsd.org>2006-04-13 11:55:08 +0000
commit7503970d10c1213afb12d3a029db8e2122bc798e (patch)
tree402baaa9cff73fe3c2dd66e36ce75cca77feb2e7
parent198e0ac5f5a49c0eef6e9998e681c8a637372e4d (diff)
Add support for "local" to ike rules. Allows to specify the local IP to be
used on a multi-homed machine. Also, relax order of peer/local keywords. ok markus@
-rw-r--r--sbin/ipsecctl/ike.c14
-rw-r--r--sbin/ipsecctl/ipsec.conf.515
-rw-r--r--sbin/ipsecctl/parse.y84
3 files changed, 71 insertions, 42 deletions
diff --git a/sbin/ipsecctl/ike.c b/sbin/ipsecctl/ike.c
index 2993f4fd754..2dd852162d1 100644
--- a/sbin/ipsecctl/ike.c
+++ b/sbin/ipsecctl/ike.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ike.c,v 1.23 2006/03/31 14:11:39 hshoexer Exp $ */
+/* $OpenBSD: ike.c,v 1.24 2006/04/13 11:55:07 hshoexer Exp $ */
/*
* Copyright (c) 2005 Hans-Joerg Hoexer <hshoexer@openbsd.org>
*
@@ -32,8 +32,8 @@
#include "ipsecctl.h"
static void ike_section_general(struct ipsec_rule *, FILE *);
-static void ike_section_peer(struct ipsec_addr_wrap *, FILE *,
- struct ike_auth *);
+static void ike_section_peer(struct ipsec_addr_wrap *,
+ struct ipsec_addr_wrap *, FILE *, struct ike_auth *);
static void ike_section_ids(struct ipsec_addr_wrap *, struct ipsec_auth *,
FILE *, u_int8_t);
static void ike_section_ipsec(struct ipsec_addr_wrap *, struct
@@ -74,11 +74,15 @@ ike_section_general(struct ipsec_rule *r, FILE *fd)
}
static void
-ike_section_peer(struct ipsec_addr_wrap *peer, FILE *fd, struct ike_auth *auth)
+ike_section_peer(struct ipsec_addr_wrap *peer, struct ipsec_addr_wrap *local,
+ FILE *fd, struct ike_auth *auth)
{
fprintf(fd, SET "[Phase 1]:%s=peer-%s force\n", peer->name, peer->name);
fprintf(fd, SET "[peer-%s]:Phase=1 force\n", peer->name);
fprintf(fd, SET "[peer-%s]:Address=%s force\n", peer->name, peer->name);
+ if (local)
+ fprintf(fd, SET "[peer-%s:Local-address=%s force\n",
+ peer->name, local->name);
if (auth->type == IKE_AUTH_PSK)
fprintf(fd, SET "[peer-%s]:Authentication=%s force\n",
peer->name, auth->string);
@@ -336,7 +340,7 @@ static int
ike_gen_config(struct ipsec_rule *r, FILE *fd)
{
ike_section_general(r, fd);
- ike_section_peer(r->peer, fd, r->ikeauth);
+ ike_section_peer(r->peer, r->local, fd, r->ikeauth);
if (ike_section_mm(r->peer, r->mmxfs, fd, r->ikeauth) == -1)
return (-1);
ike_section_ids(r->peer, r->auth, fd, r->ikemode);
diff --git a/sbin/ipsecctl/ipsec.conf.5 b/sbin/ipsecctl/ipsec.conf.5
index f628daf7429..7fd8245eb0b 100644
--- a/sbin/ipsecctl/ipsec.conf.5
+++ b/sbin/ipsecctl/ipsec.conf.5
@@ -1,4 +1,4 @@
-.\" $OpenBSD: ipsec.conf.5,v 1.39 2006/04/12 14:48:12 hshoexer Exp $
+.\" $OpenBSD: ipsec.conf.5,v 1.40 2006/04/13 11:55:07 hshoexer Exp $
.\"
.\" Copyright (c) 2004 Mathieu Sauve-Frankel All rights reserved.
.\"
@@ -144,8 +144,7 @@ parameter specifies the address of the local endpoint of this particular
flow and can be usually left out.
The
.Ar peer
-parameter specifies the address of the remote endpoint of this
-flow.
+parameter specifies the address of the remote endpoint of this flow.
For host-to-host connections where
.Aq Ar dst
is identical to
@@ -389,6 +388,8 @@ see the file
.Aq Ar src
.Ar to
.Aq Ar dst
+.Ar local
+.Aq Ar localip
.Ar peer
.Aq Ar remote
.Xc
@@ -401,9 +402,13 @@ The keyword
.Ar any
will match any address (i.e. 0.0.0.0/0).
The
+.Ar local
+parameter specifies the local address to be used, if we are multi-homed
+or have aliases.
+Usually this parameter can be left out.
+The
.Ar peer
-parameter specifies the address of the remote endpoint of this particular
-flow.
+parameter specifies the address of the remote endpoint of this particular flow.
For host-to-host connections where
.Aq Ar dst
is identical to
diff --git a/sbin/ipsecctl/parse.y b/sbin/ipsecctl/parse.y
index d355c483e55..b2eea4a863e 100644
--- a/sbin/ipsecctl/parse.y
+++ b/sbin/ipsecctl/parse.y
@@ -1,4 +1,4 @@
-/* $OpenBSD: parse.y,v 1.57 2006/03/31 14:02:08 markus Exp $ */
+/* $OpenBSD: parse.y,v 1.58 2006/04/13 11:55:07 hshoexer Exp $ */
/*
* Copyright (c) 2002, 2003, 2004 Henning Brauer <henning@openbsd.org>
@@ -132,13 +132,14 @@ struct ipsec_rule *create_sa(u_int8_t, u_int8_t, struct ipsec_addr_wrap *,
struct ipsec_key *);
struct ipsec_rule *reverse_sa(struct ipsec_rule *, u_int32_t,
struct ipsec_key *, struct ipsec_key *);
-struct ipsec_rule *create_flow(u_int8_t, u_int8_t, struct ipsec_addr_wrap *,
+struct ipsec_rule *create_flow(u_int8_t, u_int8_t, struct
+ ipsec_addr_wrap *, struct ipsec_addr_wrap *,
struct ipsec_addr_wrap *, struct ipsec_addr_wrap *,
- struct ipsec_addr_wrap *, u_int8_t, char *, char *,
- u_int8_t);
+ u_int8_t, char *, char *, u_int8_t);
struct ipsec_rule *reverse_rule(struct ipsec_rule *);
struct ipsec_rule *create_ike(u_int8_t, struct ipsec_addr_wrap *, struct
ipsec_addr_wrap *, struct ipsec_addr_wrap *,
+ struct ipsec_addr_wrap *,
struct ipsec_transforms *, struct
ipsec_transforms *, u_int8_t, u_int8_t, char *,
char *, struct ike_auth *);
@@ -158,8 +159,11 @@ typedef struct {
struct ipsec_addr_wrap *src;
struct ipsec_addr_wrap *dst;
} hosts;
- struct ipsec_addr_wrap *local;
- struct ipsec_addr_wrap *peer;
+ struct {
+ struct ipsec_addr_wrap *peer;
+ struct ipsec_addr_wrap *local;
+ } peers;
+ struct ipsec_addr_wrap *singlehost;
struct ipsec_addr_wrap *host;
struct {
char *srcid;
@@ -205,8 +209,8 @@ typedef struct {
%type <v.tmode> tmode
%type <v.number> number
%type <v.hosts> hosts
-%type <v.local> local
-%type <v.peer> peer
+%type <v.peers> peers
+%type <v.singlehost> singlehost
%type <v.host> host
%type <v.ids> ids
%type <v.id> id
@@ -303,11 +307,11 @@ sarule : satype tmode hosts spispec transforms authkeyspec
}
;
-flowrule : FLOW satype dir proto hosts local peer ids type {
+flowrule : FLOW satype dir proto hosts peers ids type {
struct ipsec_rule *r;
- r = create_flow($3, $4, $5.src, $5.dst, $6, $7, $2,
- $8.srcid, $8.dstid, $9);
+ r = create_flow($3, $4, $5.src, $5.dst, $6.local,
+ $6.peer, $2, $7.srcid, $7.dstid, $8);
if (r == NULL)
YYERROR;
r->nr = ipsec->rule_nr++;
@@ -316,7 +320,7 @@ flowrule : FLOW satype dir proto hosts local peer ids type {
errx(1, "flowrule: ipsecctl_add_rule");
/* Create and add reverse flow rule. */
- if ($9 == TYPE_UNKNOWN && $3 == IPSEC_INOUT) {
+ if ($8 == TYPE_UNKNOWN && $3 == IPSEC_INOUT) {
r = reverse_rule(r);
r->nr = ipsec->rule_nr++;
@@ -326,11 +330,11 @@ flowrule : FLOW satype dir proto hosts local peer ids type {
}
;
-ikerule : IKE ikemode satype proto hosts peer mmxfs qmxfs ids ikeauth {
+ikerule : IKE ikemode satype proto hosts peers mmxfs qmxfs ids ikeauth {
struct ipsec_rule *r;
- r = create_ike($4, $5.src, $5.dst, $6, $7, $8, $3, $2,
- $9.srcid, $9.dstid, &$10);
+ r = create_ike($4, $5.src, $5.dst, $6.local, $6.peer,
+ $7, $8, $3, $2, $9.srcid, $9.dstid, &$10);
if (r == NULL)
YYERROR;
r->nr = ipsec->rule_nr++;
@@ -386,25 +390,36 @@ hosts : FROM host TO host {
}
;
-peer : /* empty */ { $$ = NULL; }
- | PEER STRING {
- if (($$ = host($2)) == NULL) {
- free($2);
- yyerror("could not parse host specification");
- YYERROR;
- }
- free($2);
+peers : /* empty */ {
+ $$.peer = NULL;
+ $$.local = NULL;
+ }
+ | PEER singlehost LOCAL singlehost {
+ $$.peer = $2;
+ $$.local = $4;
+ }
+ | LOCAL singlehost PEER singlehost {
+ $$.peer = $4;
+ $$.local = $2;
+ }
+ | PEER singlehost {
+ $$.peer = $2;
+ $$.local = NULL;
+ }
+ | LOCAL singlehost {
+ $$.peer = NULL;
+ $$.local = $2;
}
;
-local : /* empty */ { $$ = NULL; }
- | LOCAL STRING {
- if (($$ = host($2)) == NULL) {
- free($2);
+singlehost : /* empty */ { $$ = NULL; }
+ | STRING {
+ if (($$ = host($1)) == NULL) {
+ free($1);
yyerror("could not parse host specification");
YYERROR;
}
- free($2);
+ free($1);
}
;
@@ -507,7 +522,8 @@ transforms : {
sizeof(struct ipsec_transforms))) == NULL)
err(1, "transforms: calloc");
}
- transforms_l { $$ = ipsec_transforms; }
+ transforms_l
+ { $$ = ipsec_transforms; }
| /* empty */ {
if (($$ = calloc(1,
sizeof(struct ipsec_transforms))) == NULL)
@@ -1661,9 +1677,10 @@ reverse_rule(struct ipsec_rule *rule)
struct ipsec_rule *
create_ike(u_int8_t proto, struct ipsec_addr_wrap *src, struct ipsec_addr_wrap
- *dst, struct ipsec_addr_wrap * peer, struct ipsec_transforms *mmxfs, struct
- ipsec_transforms *qmxfs, u_int8_t satype, u_int8_t mode, char *srcid, char
- *dstid, struct ike_auth *authtype)
+ *dst, struct ipsec_addr_wrap *local, struct ipsec_addr_wrap *peer,
+ struct ipsec_transforms *mmxfs, struct ipsec_transforms *qmxfs,
+ u_int8_t satype, u_int8_t mode, char *srcid, char *dstid,
+ struct ike_auth *authtype)
{
struct ipsec_rule *r;
@@ -1695,6 +1712,9 @@ create_ike(u_int8_t proto, struct ipsec_addr_wrap *src, struct ipsec_addr_wrap
} else
r->peer = peer;
+ if (local)
+ r->local = local;
+
r->satype = satype;
r->ikemode = mode;
r->mmxfs = mmxfs;