diff --git a/src/api/api_seq.cpp b/src/api/api_seq.cpp index a7c42df4f..d64589cde 100644 --- a/src/api/api_seq.cpp +++ b/src/api/api_seq.cpp @@ -315,6 +315,17 @@ extern "C" { Z3_CATCH_RETURN(nullptr); } + Z3_ast Z3_API Z3_mk_re_power(Z3_context c, Z3_ast r, unsigned n) { + Z3_TRY; + LOG_Z3_mk_re_power(c, r, n); + RESET_ERROR_CODE(); + app* a = mk_c(c)->sutil().re.mk_power(to_expr(r), n); + mk_c(c)->save_ast_trail(a); + RETURN_Z3(of_ast(a)); + Z3_CATCH_RETURN(nullptr); + } + + MK_UNARY(Z3_mk_re_plus, mk_c(c)->get_seq_fid(), OP_RE_PLUS, SKIP); MK_UNARY(Z3_mk_re_star, mk_c(c)->get_seq_fid(), OP_RE_STAR, SKIP); MK_UNARY(Z3_mk_re_option, mk_c(c)->get_seq_fid(), OP_RE_OPTION, SKIP); diff --git a/src/api/java/Context.java b/src/api/java/Context.java index 466047c16..62ffcd585 100644 --- a/src/api/java/Context.java +++ b/src/api/java/Context.java @@ -2200,6 +2200,14 @@ public class Context implements AutoCloseable { return (ReExpr) Expr.create(this, Native.mkReStar(nCtx(), re.getNativeObject())); } + /** + * Create power regular expression. + */ + public ReExpr mkLoop(Expr> re, int n) + { + return (ReExpr) Expr.create(this, Native.mkRePower(nCtx(), re.getNativeObject(), n)); + } + /** * Take the lower and upper-bounded Kleene star of a regular expression. */ diff --git a/src/api/z3_api.h b/src/api/z3_api.h index d8c817933..d7dd0a332 100644 --- a/src/api/z3_api.h +++ b/src/api/z3_api.h @@ -3821,6 +3821,13 @@ extern "C" { */ Z3_ast Z3_API Z3_mk_re_loop(Z3_context c, Z3_ast r, unsigned lo, unsigned hi); + /** + \brief Create a power regular expression. + + def_API('Z3_mk_re_power', AST, (_in(CONTEXT), _in(AST), _in(UINT))) + */ + Z3_ast Z3_API Z3_mk_re_power(Z3_context c, Z3_ast, unsigned n); + /** \brief Create the intersection of the regular languages. diff --git a/src/ast/seq_decl_plugin.cpp b/src/ast/seq_decl_plugin.cpp index 091f77f5c..f4cf2ecaa 100644 --- a/src/ast/seq_decl_plugin.cpp +++ b/src/ast/seq_decl_plugin.cpp @@ -1053,6 +1053,12 @@ sort* seq_util::rex::to_seq(sort* re) { return to_sort(re->get_parameter(0).get_ast()); } +app* seq_util::rex::mk_power(expr* r, unsigned n) { + parameter param(n); + return m.mk_app(m_fid, OP_RE_POWER, 1, ¶m, 1, &r); +} + + app* seq_util::rex::mk_loop(expr* r, unsigned lo) { parameter param(lo); return m.mk_app(m_fid, OP_RE_LOOP, 1, ¶m, 1, &r); diff --git a/src/ast/seq_decl_plugin.h b/src/ast/seq_decl_plugin.h index 9c76298b0..ddde7fa6a 100644 --- a/src/ast/seq_decl_plugin.h +++ b/src/ast/seq_decl_plugin.h @@ -502,6 +502,7 @@ public: app* mk_star(expr* r) { return m.mk_app(m_fid, OP_RE_STAR, r); } app* mk_plus(expr* r) { return m.mk_app(m_fid, OP_RE_PLUS, r); } app* mk_opt(expr* r) { return m.mk_app(m_fid, OP_RE_OPTION, r); } + app* mk_power(expr* r, unsigned n); app* mk_loop(expr* r, unsigned lo); app* mk_loop(expr* r, unsigned lo, unsigned hi); expr* mk_loop_proper(expr* r, unsigned lo, unsigned hi);