forked from GitHub/gf-core
writePGF now allows to select list of languages
This commit is contained in:
@@ -847,7 +847,7 @@ pgfCommands = Map.fromList [
|
||||
prGrammar pgf opts
|
||||
| isOpt "pgf" opts = do
|
||||
let outfile = valStrOpts "file" (abstractName pgf ++ ".pgf") opts
|
||||
restricted $ writePGF outfile pgf
|
||||
restricted $ writePGF outfile pgf (Just (map concreteName (optLangs pgf opts)))
|
||||
putStrLn $ "wrote file " ++ outfile
|
||||
return void
|
||||
| isOpt "cats" opts = return $ fromString $ unwords $ categories pgf
|
||||
|
||||
@@ -180,7 +180,7 @@ writeGrammar :: Options -> PGF -> IOE ()
|
||||
writeGrammar opts pgf =
|
||||
if fst (flag optLinkTargets opts)
|
||||
then do let outfile = outputPath opts (grammarName opts pgf <.> "pgf")
|
||||
writing opts outfile (writePGF outfile pgf)
|
||||
writing opts outfile (writePGF outfile pgf Nothing)
|
||||
else return ()
|
||||
|
||||
writeOutput :: Options -> FilePath-> String -> IOE ()
|
||||
|
||||
@@ -244,6 +244,7 @@ void pgf_merge_pgf(PgfDB *db, PgfRevision revision,
|
||||
PGF_API
|
||||
void pgf_write_pgf(const char* fpath,
|
||||
PgfDB *db, PgfRevision revision,
|
||||
PgfText **langs,
|
||||
PgfExn* err)
|
||||
{
|
||||
FILE *out = NULL;
|
||||
@@ -258,7 +259,7 @@ void pgf_write_pgf(const char* fpath,
|
||||
DB_scope scope(db, READER_SCOPE);
|
||||
ref<PgfPGF> pgf = db->revision2pgf(revision);
|
||||
|
||||
PgfWriter wtr(out);
|
||||
PgfWriter wtr(langs, out);
|
||||
wtr.write_pgf(pgf);
|
||||
}
|
||||
} PGF_API_END
|
||||
|
||||
@@ -287,6 +287,7 @@ void pgf_merge_pgf(PgfDB *db, PgfRevision revision,
|
||||
PGF_API_DECL
|
||||
void pgf_write_pgf(const char* fpath,
|
||||
PgfDB *db, PgfRevision revision,
|
||||
PgfText **langs, // null terminated list or null
|
||||
PgfExn* err);
|
||||
|
||||
PGF_API_DECL
|
||||
|
||||
@@ -2,9 +2,10 @@
|
||||
#include "data.h"
|
||||
#include "writer.h"
|
||||
|
||||
PgfWriter::PgfWriter(FILE *out)
|
||||
PgfWriter::PgfWriter(PgfText **langs, FILE *out)
|
||||
{
|
||||
this->out = out;
|
||||
this->langs = langs;
|
||||
this->abstract = 0;
|
||||
}
|
||||
|
||||
@@ -411,6 +412,22 @@ void PgfWriter::write_printname(ref<PgfConcrPrintname> printname)
|
||||
|
||||
void PgfWriter::write_concrete(ref<PgfConcr> concr)
|
||||
{
|
||||
if (langs != NULL) {
|
||||
bool found = false;
|
||||
PgfText** p = langs;
|
||||
while (*p) {
|
||||
if (textcmp(*p, &concr->name) == 0) {
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
p++;
|
||||
}
|
||||
|
||||
if (!found) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
seq_ids.start(concr);
|
||||
|
||||
write_name(&concr->name);
|
||||
@@ -431,5 +448,16 @@ void PgfWriter::write_pgf(ref<PgfPGF> pgf)
|
||||
write_namespace<PgfFlag>(pgf->gflags, &PgfWriter::write_flag);
|
||||
|
||||
write_abstract(ref<PgfAbstr>::from_ptr(&pgf->abstract));
|
||||
write_namespace<PgfConcr>(pgf->concretes, &PgfWriter::write_concrete);
|
||||
|
||||
if (langs == NULL)
|
||||
write_len(namespace_size(pgf->concretes));
|
||||
else {
|
||||
size_t len = 0;
|
||||
PgfText** p = langs;
|
||||
while (*p) {
|
||||
len++; p++;
|
||||
}
|
||||
write_len(len);
|
||||
}
|
||||
write_namespace_helper<PgfConcr>(pgf->concretes, &PgfWriter::write_concrete);
|
||||
}
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
class PGF_INTERNAL_DECL PgfWriter
|
||||
{
|
||||
public:
|
||||
PgfWriter(FILE *out);
|
||||
PgfWriter(PgfText **langs, FILE *out);
|
||||
|
||||
void write_uint8(uint8_t b);
|
||||
void write_u16be(uint16_t u);
|
||||
@@ -66,6 +66,7 @@ private:
|
||||
void write_presult(ref<ref<PgfPResult>> r) { write_presult(*r); };
|
||||
|
||||
FILE *out;
|
||||
PgfText **langs;
|
||||
|
||||
ref<PgfAbstr> abstract;
|
||||
PgfPhrasetableIds seq_ids;
|
||||
|
||||
@@ -188,11 +188,15 @@ newNGF abs_name mb_fpath =
|
||||
fptr <- newForeignPtrEnv pgf_free_revision c_db c_revision
|
||||
return (PGF c_db fptr Map.empty)
|
||||
|
||||
writePGF :: FilePath -> PGF -> IO ()
|
||||
writePGF fpath p =
|
||||
writePGF :: FilePath -> PGF -> Maybe [ConcName] -> IO ()
|
||||
writePGF fpath p mb_langs =
|
||||
withCString fpath $ \c_fpath ->
|
||||
withForeignPtr (a_revision p) $ \c_revision ->
|
||||
withPgfExn "writePGF" (pgf_write_pgf c_fpath (a_db p) c_revision)
|
||||
maybe (\f -> f nullPtr) (withLangs []) mb_langs $ \c_langs ->
|
||||
withPgfExn "writePGF" (pgf_write_pgf c_fpath (a_db p) c_revision c_langs)
|
||||
where
|
||||
withLangs clangs [] f = withArray0 nullPtr (reverse clangs) f
|
||||
withLangs clangs (lang:langs) f = withText lang $ \clang -> withLangs (clang:clangs) langs f
|
||||
|
||||
showPGF :: PGF -> String
|
||||
showPGF p =
|
||||
|
||||
@@ -78,7 +78,7 @@ foreign import ccall pgf_new_ngf :: Ptr PgfText -> CString -> Ptr (Ptr PGF) -> P
|
||||
|
||||
foreign import ccall pgf_merge_pgf :: Ptr PgfDB -> Ptr PGF -> CString -> Ptr PgfExn -> IO ()
|
||||
|
||||
foreign import ccall pgf_write_pgf :: CString -> Ptr PgfDB -> Ptr PGF -> Ptr PgfExn -> IO ()
|
||||
foreign import ccall pgf_write_pgf :: CString -> Ptr PgfDB -> Ptr PGF -> Ptr (Ptr PgfText) -> Ptr PgfExn -> IO ()
|
||||
|
||||
foreign import ccall "pgf_free_revision" pgf_free_revision_ :: Ptr PgfDB -> Ptr PGF -> IO ()
|
||||
|
||||
|
||||
@@ -517,18 +517,45 @@ PGF_dealloc(PGFObject *self)
|
||||
}
|
||||
|
||||
static PyObject *
|
||||
PGF_writePGF(PGFObject *self, PyObject *args)
|
||||
PGF_writePGF(PGFObject *self, PyObject *args, PyObject *kwargs)
|
||||
{
|
||||
char *kwds[] = {"","langs",NULL};
|
||||
|
||||
const char *fpath;
|
||||
if (!PyArg_ParseTuple(args, "s", &fpath))
|
||||
PyObject *py_langs = NULL;
|
||||
if (!PyArg_ParseTupleAndKeywords(args, kwargs, "s|O!", &kwds[0], &fpath, &PyList_Type, &py_langs))
|
||||
return NULL;
|
||||
|
||||
PgfText **langs = NULL;
|
||||
if (py_langs != NULL) {
|
||||
size_t len = PyList_Size(py_langs);
|
||||
langs = (PgfText **) alloca((len+1)*sizeof(PgfText*));
|
||||
for (size_t i = 0; i < len; i++) {
|
||||
langs[i] = PyUnicode_AsPgfText(PyList_GetItem(py_langs,i));
|
||||
if (!langs[i]) {
|
||||
while (i > 0) {
|
||||
FreePgfText(langs[--i]);
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
langs[len] = NULL;
|
||||
}
|
||||
|
||||
PgfExn err;
|
||||
pgf_write_pgf(fpath, self->db, self->revision, &err);
|
||||
pgf_write_pgf(fpath, self->db, self->revision, langs, &err);
|
||||
if (handleError(err) != PGF_EXN_NONE) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (langs != NULL) {
|
||||
PgfText **p = langs;
|
||||
while (*p) {
|
||||
FreePgfText(*p);
|
||||
p++;
|
||||
}
|
||||
}
|
||||
|
||||
Py_RETURN_NONE;
|
||||
}
|
||||
|
||||
@@ -1152,7 +1179,7 @@ PGF_embed(PGFObject* self, PyObject *modname)
|
||||
#endif
|
||||
|
||||
static PyMethodDef PGF_methods[] = {
|
||||
{"writePGF", (PyCFunction)PGF_writePGF, METH_VARARGS,
|
||||
{"writePGF", (PyCFunction)PGF_writePGF, METH_VARARGS | METH_KEYWORDS,
|
||||
"Writes to a PGF file"},
|
||||
{"categoryContext", (PyCFunction)PGF_categoryContext, METH_VARARGS,
|
||||
"Returns the context for a given category"
|
||||
|
||||
Reference in New Issue
Block a user