Commit a7972639 authored by Tom Niget's avatar Tom Niget

Finish migrating almost everything to dot, all examples compile again

parent 898d3135
......@@ -21,7 +21,7 @@ public:
}
};
struct function {};
struct method {};
template <typename Func, typename Self>
struct boundmethod {
......@@ -37,19 +37,20 @@ struct boundmethod {
};
template <typename Obj, std::derived_from<function> Attr>
auto bind(Obj obj, Attr attr) {
template <typename Obj, std::derived_from<method> Attr>
auto dot_bind(Obj obj, Attr attr) {
return boundmethod(attr, obj);
}
template <typename Obj, typename Attr>
requires (! std::derived_from<Attr, function>)
auto bind(Obj, Attr attr) {
requires (! std::derived_from<Attr, method>)
auto dot_bind(Obj, Attr attr) {
return attr;
}
#define dot(OBJ, NAME) [](auto && obj) -> auto { return bind(obj, obj.NAME); }(OBJ)
#define dotp(OBJ, NAME) [](auto && obj) -> auto { return bind(obj, obj->NAME); }(OBJ)
#define dot(OBJ, NAME) [](auto && obj) -> auto { return dot_bind(obj, obj.NAME); }(OBJ)
#define dotp(OBJ, NAME) [](auto && obj) -> auto { return dot_bind(obj, obj->NAME); }(OBJ)
#define dots(OBJ, NAME) [](auto && obj) -> auto { return std::remove_reference<decltype(obj)>::type::type::NAME; }(OBJ)
#endif // TYPON_BASEDEF_HPP
......@@ -22,19 +22,28 @@
[[noreturn]] inline void TYPON_UNREACHABLE() { std::abort(); }
#endif
#define _Args(...) __VA_ARGS__
#define COMMA() ,
#define METHOD(ret, name, args, ...) \
struct { \
ret operator() args __VA_ARGS__ type *self; \
} name{this};
static constexpr struct name##_s : method { \
template <typename Self> ret operator() args const __VA_ARGS__ \
} name{};
#define METHOD_GEN(gen, ret, name, args, ...) \
static constexpr struct name##_s : method { \
template <typename Self, _Args gen> ret operator() args const __VA_ARGS__ \
} name{};
#define FUNCTION(ret, name, args, ...) \
struct { \
ret operator() args __VA_ARGS__ \
} name;
} static constexpr name;
using namespace std::literals;
template <typename T>
concept PySmartPtr = requires { typename T::element_type; };
template <typename T>
concept PyUserType = requires { typename T::type; };
......@@ -46,6 +55,10 @@ template <PyUserType T> struct RealType<T> {
using type = typename T::type;
};
template <PySmartPtr T> struct RealType<T> {
using type = typename T::element_type;
};
template <typename T> using PyObj = std::shared_ptr<typename RealType<T>::type>;
template <typename T, typename... Args> auto pyobj(Args &&...args) -> PyObj<T> {
......@@ -53,6 +66,10 @@ template <typename T, typename... Args> auto pyobj(Args &&...args) -> PyObj<T> {
std::forward<Args>(args)...);
}
template <typename T, typename... Args> auto pyobj_agg(Args &&...args) -> PyObj<T> {
return std::make_shared<typename RealType<T>::type>((typename RealType<T>::type) { std::forward<Args>(args)... });
}
// typon_len
template <typename T>
......@@ -131,10 +148,10 @@ public:
#include "builtins/slice.hpp"
#include "builtins/str.hpp"
struct {
struct file_s {
struct type {
METHOD(
typon::Task<PyStr>, read, (size_t size = -1), const {
typon::Task<PyStr>, read, (Self self, size_t size = -1), {
if (size == -1) {
size = self->len;
}
......@@ -147,7 +164,7 @@ struct {
co_return std::move(buf);
})
METHOD(
typon::Task<int>, write, (const std::string &buf), const {
typon::Task<int>, write, (Self self, const std::string &buf), {
int nbytes = co_await typon::io::write(self->fd, buf);
if (nbytes < 0) {
system_error(-nbytes, "write()");
......@@ -155,24 +172,23 @@ struct {
co_return nbytes;
})
METHOD(
typon::Task<void>, close, (),
const { co_await typon::io::close(self->fd); })
typon::Task<void>, close, (Self self),
{ co_await typon::io::close(self->fd); })
METHOD(
typon::Task<void>, flush, (),
const { co_await typon::io::fsync(self->fd); })
typon::Task<void>, flush, (Self self),
{ co_await typon::io::fsync(self->fd); })
type(int fd = -1, size_t len = 0) : fd(fd), len(len) {}
type(const type &other)
: read(this), write(this), close(this), flush(this), py_enter(this),
py_exit(this), fd(other.fd), len(other.len) {}
: fd(other.fd), len(other.len) {}
METHOD(
type, py_enter, (), const { return *self; })
auto, py_enter, (Self self), { return self; })
METHOD(
typon::Task<bool>, py_exit, (), const {
co_await self->close();
typon::Task<bool>, py_exit, (Self self), {
co_await dotp(self, close)();
co_return true;
})
......@@ -181,11 +197,11 @@ struct {
};
} file;
// namespace typon {
using PyFile = decltype(file)::type;
//}
namespace typon {
using PyFile = PyObj<decltype(file)::type>;
}
typon::Task<PyFile> open(const PyStr &path, std::string_view mode) {
typon::Task<typon::PyFile> open(const PyStr &path, std::string_view mode) {
const char *path_c = path.c_str();
size_t len = 0;
struct statx statxbuf;
......@@ -233,7 +249,7 @@ typon::Task<PyFile> open(const PyStr &path, std::string_view mode) {
std::cerr << path << "," << flags << std::endl;
system_error(-fd, "openat()");
}
co_return PyFile(fd, len);
co_return pyobj<typon::PyFile>(fd, len);
}
#include "../typon/generator.hpp"
......@@ -261,4 +277,21 @@ struct lvalue_or_rvalue {
};
namespace typon {
template< class... Types >
using PyTuple = std::tuple<Types...>;
}
template<typename T>
auto& iter_fix_ref(T& obj) { return obj; }
template<PySmartPtr T>
auto& iter_fix_ref(T& obj) { return *obj; }
namespace std {
template <class T> auto begin(std::shared_ptr<T> &obj) { return dotp(obj, begin)(); }
template <class T> auto end(std::shared_ptr<T> &obj) { return dotp(obj, end)(); }
}
#endif // TYPON_BUILTINS_HPP
......@@ -18,7 +18,9 @@ public:
template <class InputIterator>
PyBytes(InputIterator first, InputIterator last) : std::string(first, last) {}
PyStr decode(const std::string &encoding = "utf-8") const;
//PyStr decode_inner(const std::string &encoding = "utf-8") const;
METHOD(PyStr, decode, (Self self, const std::string &encoding = "utf-8"), ;)
};
#endif // TYPON_BYTES_H
......
......@@ -83,6 +83,8 @@ public:
template <typename K, typename V>
PyDict(std::initializer_list<std::pair<K, V>>) -> PyDict<K, V>;*/
namespace typon {
template <typename K, typename V> class PyDict {
public:
PyDict(std::shared_ptr<std::unordered_map<K, V>> &&m) : _m(std::move(m)) {}
......@@ -93,8 +95,10 @@ public:
: _m(std::make_shared<std::unordered_map<K, V>>(std::move(m))) {}
PyDict() : _m(std::make_shared<std::unordered_map<K, V>>()) {}
template<typename... Args>
PyDict(Args&&... args) : _m(std::make_shared<std::unordered_map<K, V>>(std::forward<Args>(args)...)) {}
template <typename... Args>
PyDict(Args &&...args)
: _m(std::make_shared<std::unordered_map<K, V>>(
std::forward<Args>(args)...)) {}
auto begin() const { return _m->begin(); }
auto end() const { return _m->end(); }
......@@ -128,4 +132,6 @@ private:
std::shared_ptr<std::unordered_map<K, V>> _m;
};
}
#endif // TYPON_DICT_HPP
......@@ -11,6 +11,8 @@
//#include <nanobind/stl/detail/nb_list.h>
#include <pybind11/stl.h>
namespace typon {
template <typename T> class PyList {
public:
PyList(std::shared_ptr<std::vector<T>> &&v) : _v(std::move(v)) {}
......@@ -26,25 +28,19 @@ public:
auto end() const { return _v->end(); }
auto append(const T &x) { _v->push_back(x); }
METHOD(auto, append, (Self self, const T &x), {
self._v->push_back(x);
})
struct : function {
template<typename Self> auto operator()(Self self, const T &x) const {
METHOD(auto, py_contains, (Self self, const T &x), {
return std::find(self.begin(), self.end(), x) != self.end();
}
} static constexpr py_contains;
})
auto size() const {
return _v->size();
}
auto size() const { return _v->size(); }
void push_back(const T& value) {
_v->push_back(value);
}
void push_back(const T &value) { _v->push_back(value); }
void clear() {
_v->clear();
}
void clear() { _v->clear(); }
/*operator std::vector<T>() const {
return std::vector<T>(this->begin(), this->end());
......@@ -94,13 +90,20 @@ private:
std::shared_ptr<std::vector<T>> _v;
};
template <typename T> PyList<T> list(std::initializer_list<T> &&v) {
return PyList<T>(std::move(v));
}
template <typename T> typon::PyList<T> list(std::initializer_list<T> &&v) {
return typon::PyList<T>(std::move(v));
}
namespace PYBIND11_NAMESPACE { namespace detail {
namespace PYBIND11_NAMESPACE {
namespace detail {
template <typename Type>
struct type_caster<PyList<Type>> : list_caster<PyList<Type>, Type> {};
struct type_caster<typon::PyList<Type>> : list_caster<typon::PyList<Type>, Type> {};
}}
/*NAMESPACE_BEGIN(NB_NAMESPACE)
......
......@@ -7,6 +7,8 @@
#include <unordered_set>
namespace typon {
template <typename T> class PySet : public std::unordered_set<T> {
public:
PySet(std::unordered_set<T> &&s) : std::unordered_set<T>(std::move(s)) {}
......@@ -69,8 +71,10 @@ public:
}
};
template <typename T> PySet<T> set(std::initializer_list<T> &&s) {
return PySet<T>(std::move(s));
}
template <typename T> typon::PySet<T> set(std::initializer_list<T> &&s) {
return typon::PySet<T>(std::move(s));
}
#endif // TYPON_SET_HPP
......@@ -29,16 +29,23 @@ public:
template <class InputIterator>
PyStr(InputIterator first, InputIterator last) : std::string(first, last) {}
PyBytes encode(const std::string &encoding = "utf-8") const {
return PyBytes(this->begin(), this->end());
}
template <typename... T> PyStr format(T &&...args) const {
return PyStr(fmt::format(fmt::runtime(*this), std::forward<T>(args)...));
}
METHOD(PyBytes, encode, (Self self, const std::string &encoding = "utf-8"), {
return PyBytes(self.begin(), self.end());
})
METHOD_GEN((typename... T), PyStr, format, (Self self, T &&...args), {
return PyStr(fmt::format(fmt::runtime(self), std::forward<T>(args)...));
})
bool startswith(const std::string &s) const { return this->starts_with(s); }
METHOD(bool, startswith, (Self self, const std::string &s), {
return self.starts_with(s);
})
METHOD(int, find, (Self self, const std::string &s), {
auto pos = self.std::string::find(s);
return pos == std::string::npos ? -1 : pos;
})
PyStr operator[](PySlice slice) const {
auto [len, new_slice] = slice.adjust_indices(this->size());
......@@ -80,14 +87,19 @@ public:
return this->begin()[index];
}
operator int() const {
return std::stoi(*this);
}
};
inline constexpr PyStr operator""_ps(const char *s, size_t len) noexcept {
return PyStr(s, len);
}
PyStr PyBytes::decode(const std::string &encoding) const {
return PyStr(this->begin(), this->end());
template<typename Self>
PyStr PyBytes::decode_s::operator()(Self self, const std::string &encoding) const {
return PyStr(self.begin(), self.end());
}
template <typename T> PyStr str(const T &x) {
......
......@@ -19,7 +19,7 @@ struct hashlib_t {
unsigned long len);
typedef int (*openssl_final)(unsigned char *md, void *context);
struct {
struct _Hash_s {
struct type {
type(PyObj<void> context, openssl_update update, openssl_final final,
......@@ -31,19 +31,18 @@ struct hashlib_t {
type(const type &other)
: _context(other._context), _update(other._update),
_final(other._final), _diglen(other._diglen), update(this),
hexdigest(this) {}
_final(other._final), _diglen(other._diglen) {}
PyObj<void> _context;
openssl_update _update;
openssl_final _final;
int _diglen;
METHOD(int, update, (std::string val), {
METHOD(int, update, (Self self, std::string val), {
return self->_update(self->_context.get(), &val[0], val.size());
})
METHOD(std::string, hexdigest, (), {
METHOD(std::string, hexdigest, (Self self), {
auto resbuf = new unsigned char[self->_diglen];
self->_final(resbuf, self->_context.get());
std::string hexres;
......@@ -60,21 +59,21 @@ struct hashlib_t {
FUNCTION(auto, md5, (), {
auto ctx = pyobj<MD5_CTX>();
MD5_Init(ctx.get());
return decltype(_Hash)::type(ctx, (openssl_update)MD5_Update,
return pyobj<_Hash_s>(ctx, (openssl_update)MD5_Update,
(openssl_final)MD5_Final, MD5_DIGEST_LENGTH);
})
FUNCTION(auto, sha1, (), {
auto ctx = pyobj<SHA_CTX>();
SHA1_Init(ctx.get());
return decltype(_Hash)::type(ctx, (openssl_update)SHA1_Update,
return pyobj<_Hash_s>(ctx, (openssl_update)SHA1_Update,
(openssl_final)SHA1_Final, SHA_DIGEST_LENGTH);
})
FUNCTION(auto, sha256, (), {
auto ctx = pyobj<SHA256_CTX>();
SHA256_Init(ctx.get());
return decltype(_Hash)::type(ctx, (openssl_update)SHA256_Update,
return pyobj<_Hash_s>(ctx, (openssl_update)SHA256_Update,
(openssl_final)SHA256_Final,
SHA256_DIGEST_LENGTH);
})
......@@ -82,7 +81,7 @@ struct hashlib_t {
FUNCTION(auto, sha512, (), {
auto ctx = pyobj<SHA512_CTX>();
SHA512_Init(ctx.get());
return decltype(_Hash)::type(ctx, (openssl_update)SHA512_Update,
return pyobj<_Hash_s>(ctx, (openssl_update)SHA512_Update,
(openssl_final)SHA512_Final,
SHA512_DIGEST_LENGTH);
})
......@@ -92,8 +91,8 @@ struct hashlib_t {
auto &get_all() { return all; }
} // namespace py_hashlib
// namespace typon {
using Py_Hash = decltype(py_hashlib::all._Hash)::type;
//}
namespace typon {
using Py_Hash = PyObj<py_hashlib::hashlib_t::_Hash_s>;
}
#endif // TYPON_HASHLIB_HPP
......@@ -9,11 +9,11 @@
namespace py_json {
struct json_t {
template <typename T> typon::Task<void> dump(const T &x, PyFile &fp) {
FUNCTION(template <typename T> typon::Task<void>, dump, (const T &x, typon::PyFile &fp), {
std::stringstream ss;
repr_to(x, ss);
co_await fp.write(ss.str());
}
co_await dotp(fp, write)(ss.str());
})
} all;
auto &get_all() { return all; }
......
......@@ -24,7 +24,7 @@ struct os_t {
FUNCTION(
auto, fsdecode, (std::string s) { return s; })
struct {
struct Stat_Result_s {
struct type {
int st_mode;
unsigned long long st_ino;
......@@ -44,32 +44,32 @@ struct os_t {
};
} Stat_Result;
struct {
struct DirEntry_s {
struct type {
PyStr name;
PyStr path;
};
} DirEntry;
struct {
struct _Scandiriterator_s {
struct type {
using value_type = decltype(DirEntry)::type;
using reference = decltype(DirEntry)::type;
using value_type = PyObj<DirEntry_s>;
using reference = PyObj<DirEntry_s>;
METHOD(type, py_enter, (), { return *self; })
METHOD(void, py_exit, (), {
METHOD(auto, py_enter, (Self self), { return self; })
METHOD(void, py_exit, (Self self), {
if (self->namelist) {
free(self->namelist);
}
})
METHOD(auto, begin, (), { return *self; })
METHOD(auto, end, (),
METHOD(auto, begin, (Self self), { return *self; })
METHOD(auto, end, (Self self),
{ return type(self->basepath, self->namelist, self->n, self->n); })
decltype(DirEntry)::type operator*() {
auto operator*() {
auto name = PyStr(this->namelist[this->current]->d_name);
return decltype(DirEntry)::type{name, this->basepath + name};
return pyobj_agg<DirEntry_s>(name, this->basepath + name);
}
type(const PyStr &basepath, struct dirent **namelist, int n,
......@@ -95,7 +95,7 @@ struct os_t {
};
} _Scandiriterator;
FUNCTION(typon::Task<decltype(Stat_Result)::type>, stat, (const PyStr &path),
FUNCTION(typon::Task<PyObj<Stat_Result_s>>, stat, (const PyStr &path),
{
const char *path_c = path.c_str();
struct statx statxbuf;
......@@ -103,7 +103,7 @@ struct os_t {
STATX_SIZE, &statxbuf)) {
system_error(-err, "statx()");
}
co_return decltype(Stat_Result)::type{
co_return PyObj<Stat_Result_s>(new Stat_Result_s::type{
statxbuf.stx_mode,
statxbuf.stx_ino,
makedev(statxbuf.stx_dev_major, statxbuf.stx_dev_minor),
......@@ -118,17 +118,17 @@ struct os_t {
statxbuf.stx_blksize,
makedev(statxbuf.stx_rdev_major, statxbuf.stx_rdev_minor),
0,
statxbuf.stx_btime.tv_sec + statxbuf.stx_btime.tv_nsec / 1e9};
statxbuf.stx_btime.tv_sec + statxbuf.stx_btime.tv_nsec / 1e9});
})
FUNCTION(decltype(_Scandiriterator)::type, scandir, (const PyStr &path), {
FUNCTION(PyObj<_Scandiriterator_s>, scandir, (const PyStr &path), {
const char *path_c = path.c_str();
struct dirent **namelist;
int n = ::scandir(path_c, &namelist, no_special, alphasort);
if (n < 0) {
system_error(-n, "scandir()");
}
return decltype(_Scandiriterator)::type(path, namelist, n);
return pyobj<_Scandiriterator_s>(path, namelist, n);
});
FUNCTION(PyStr, readlink, (const PyStr &path), {
......@@ -145,7 +145,9 @@ struct os_t {
auto &get_all() { return all; }
} // namespace py_os
using PyStat_Result = decltype(py_os::all.Stat_Result)::type;
using Py_Scandiriterator = decltype(py_os::all.scandir({}));
namespace typon {
using PyStat_Result = PyObj<py_os::os_t::Stat_Result_s>;
using Py_Scandiriterator = PyObj<py_os::os_t::_Scandiriterator_s>;
}
#endif // TYPON_OS_HPP
......@@ -15,38 +15,40 @@ struct socket_t {
#undef AF_INET6
#undef SOL_SOCKET
#undef SO_REUSEADDR
#undef AF_UNIX
static constexpr int SOCK_STREAM = 1;
static constexpr int AF_INET6 = 10;
static constexpr int SOL_SOCKET = 1;
static constexpr int SO_REUSEADDR = 2;
static constexpr int AF_UNIX = 1;
struct {
struct socket_s {
struct type {
METHOD(typon::Task<std::tuple<type COMMA() std::string>>, accept, (), {
METHOD(typon::Task<std::tuple<PyObj<type> COMMA() std::string>>, accept, (Self self), {
int connfd = co_await typon::io::accept(self->fd, NULL, NULL);
if (connfd < 0) {
system_error(-connfd, "accept()");
}
co_return std::make_tuple(type(connfd), std::string("")); // TODO
co_return std::make_tuple(pyobj<type>(connfd), std::string("")); // TODO
})
METHOD(typon::Task<void>, close, (),
METHOD(typon::Task<void>, close, (Self self),
{ co_await typon::io::close(self->fd); })
METHOD(void, listen, (int backlog), {
METHOD(void, listen, (Self self, int backlog), {
if (::listen(self->fd, backlog) < 0) {
self->close();
dotp(self, close)();
system_error(errno, "listen()");
}
})
METHOD(void, setsockopt, (int level, int optname, int optval), {
METHOD(void, setsockopt, (Self self, int level, int optname, int optval), {
if (::setsockopt(self->fd, level, optname, &optval, sizeof(int)) < 0) {
system_error(errno, "setsockopt()");
}
})
METHOD(void, bind, (std::tuple<std::string COMMA() int> address), {
METHOD(void, bind, (Self self, std::tuple<std::string COMMA() int> address), {
auto [host, port] = address;
sockaddr_in6 addr;
std::memset(&addr, 0, sizeof(addr));
......@@ -58,16 +60,16 @@ struct socket_t {
}
})
METHOD(typon::Task<PyBytes>, recv, (int bufsize), {
METHOD(typon::Task<PyBytes>, recv, (Self self, int bufsize), {
PyBytes buf(bufsize, '\0');
co_await typon::io::recv(self->fd, buf.data(), buf.size(), 0);
co_return std::move(buf);
})
METHOD(typon::Task<void>, send, (PyBytes data), {
METHOD(typon::Task<void>, send, (Self self, PyBytes data), {
if (int sbytes = co_await typon::io::send(self->fd, data, 0);
sbytes < 0) {
co_await self->close();
co_await dotp(self, close)();
system_error(-sbytes, "send()");
}
})
......@@ -75,27 +77,41 @@ struct socket_t {
type(int fd = -1) : fd(fd) {}
type(const type &other)
: fd(other.fd), accept(this), close(this), listen(this),
setsockopt(this), bind(this), recv(this), send(this) {}
: fd(other.fd) {}
int fd;
};
type operator()(int family, int type_) {
auto operator()(int family, int type_) {
if (int fd = ::socket(family, type_, 0); fd >= 0) {
return type(fd);
return pyobj<type>(fd);
} else {
system_error(errno, "socket()");
}
}
} socket;
FUNCTION(auto, getaddrinfo, (std::string host, int port, int family=0, int type_=0, int proto=0, int flags=0), {
/*addrinfo hints;
std::memset(&hints, 0, sizeof(hints));
hints.ai_family = family;
hints.ai_socktype = type_;
hints.ai_protocol = proto;
hints.ai_flags = flags;
addrinfo *res;
if (int err = ::getaddrinfo(host.c_str(), port.c_str(), &hints, &res); err != 0) {
system_error(err, "getaddrinfo()");
}
return res;*/
return 123;
})
} all;
auto &get_all() { return all; }
} // namespace py_socket
namespace typon {
using PySocket = decltype(py_socket::all.socket)::type;
using PySocket = PyObj<py_socket::socket_t::socket_s>;
}
#endif // TYPON_SOCKET_HPP
......@@ -13,7 +13,7 @@ struct sys_t {
static constexpr auto &stdin = std::cin;
static constexpr auto &stdout = std::cout;
static constexpr auto &stderr = std::cerr;
PyList<PyStr> argv;
typon::PyList<PyStr> argv;
FUNCTION(void, exit, (int code), {
std::exit(code);
......
ALT_RUNNER="clang++-16 -O3 -Wno-return-type -Wno-unused-result -I../rt/include -std=c++20 -o {name_bin} {name_cpp_posix} -pthread -luring && {name_bin}"
\ No newline at end of file
ALT_RUNNER='ssh tom@ubuntu-nexedi "cd /mnt/hgfs/C/GitHub/typon/trans; clang++-16 -O3 -Wno-deprecated-declarations -Wno-return-type -Wno-unused-result -I../rt/include -std=c++20 $(python3 -m pybind11 --includes) -o {name_bin} {name_cpp_posix} -pthread -luring -lfmt -lssl -lcrypto -lpython3.10 && {run_file} && {name_bin}"'
# norun
# nocompile
import sys
import socket
from socket import socket, getaddrinfo, AF_UNIX, SOCK_STREAM
if __name__ == "__main__":
s: socket.socket
s: socket
if len(sys.argv) == 3:
host = sys.argv[1]
port = sys.argv[2]
family, _, _, _, addr = socket.getaddrinfo(host, int(port))[0]
s = socket.socket(family, socket.SOCK_STREAM)
family, _, _, _, addr = getaddrinfo(host, int(port))[0]
s = socket(family, SOCK_STREAM)
s.connect(addr)
elif len(sys.argv) == 2:
path = sys.argv[1]
......@@ -18,7 +19,7 @@ if __name__ == "__main__":
addr = '\0' + path[1:]
else:
addr = path
s = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
s = socket(AF_UNIX, SOCK_STREAM)
s.connect(addr)
else:
print("Usage:", sys.argv[0] , "host port | path | @abstract")
......
import sys
import math
def g():
return 1,2,3
if __name__ == "__main__":
a = "hello, world"
print(a, a[::-1])
\ No newline at end of file
if True:
a, b, c = g()
\ No newline at end of file
......@@ -91,7 +91,7 @@ class NodeVisitor(UniversalVisitor):
#yield f"TYPEVAR_{node.name}";return
raise UnresolvedTypeVariableError(node)
elif isinstance(node, TypeOperator):
yield "Py" + node.name.title()
yield "typon::Py" + node.name.title()
if node.args:
yield "<"
yield from join(", ", map(self.visit, node.args))
......
......@@ -121,11 +121,16 @@ class BlockVisitor(NodeVisitor):
yield "}"
def visit_lvalue(self, lvalue: ast.expr, declare: bool = False) -> Iterable[str]:
def visit_lvalue(self, lvalue: ast.expr, declare: bool | list[bool] = False) -> Iterable[str]:
if isinstance(lvalue, ast.Tuple):
for name, decl, ty in zip(lvalue.elts, declare, lvalue.type.args):
if declare:
yield from self.visit_lvalue(name, True)
yield ";"
yield f"std::tie({', '.join(flatmap(self.visit_lvalue, lvalue.elts))})"
elif isinstance(lvalue, ast.Name):
if lvalue.id == "_":
if not declare:
yield "std::ignore"
return
name = self.fix_name(lvalue.id)
......
......@@ -45,9 +45,9 @@ class ClassVisitor(NodeVisitor):
yield "return pyobj<type>(std::forward<T>(args)...);"
yield "}"
outer = ClassOuterVisitor(node.inner_scope)
for stmt in node.body:
yield from outer.visit(stmt)
# outer = ClassOuterVisitor(node.inner_scope)
# for stmt in node.body:
# yield from outer.visit(stmt)
yield f"}} {node.name};"
......@@ -67,7 +67,7 @@ class ClassInnerVisitor(NodeVisitor):
# from transpiler.phases.emit_cpp.block import BlockVisitor
# yield from BlockVisitor(self.scope).visit_func_new(node, FunctionEmissionKind.METHOD, True)
# yield f"}} {node.name} {{ this }};"
yield f"struct {node.name}_m_s : function {{"
yield f"struct {node.name}_m_s : method {{"
from transpiler.phases.emit_cpp.block import BlockVisitor
yield from BlockVisitor(self.scope).visit_func_new(node, FunctionEmissionKind.METHOD)
yield f"}} static constexpr {node.name} {{}};"
......
......@@ -232,7 +232,7 @@ class ExpressionVisitor(NodeVisitor):
def visit_List(self, node: ast.List) -> Iterable[str]:
if node.elts:
yield "PyList{"
yield "typon::PyList{"
yield from join(", ", map(self.reset().visit, node.elts))
yield "}"
else:
......@@ -241,7 +241,7 @@ class ExpressionVisitor(NodeVisitor):
def visit_Set(self, node: ast.Set) -> Iterable[str]:
if node.elts:
yield "PySet{"
yield "typon::PySet{"
yield from join(", ", map(self.reset().visit, node.elts))
yield "}"
else:
......@@ -275,7 +275,7 @@ class ExpressionVisitor(NodeVisitor):
yield from self.visit_unary_operation(node.op, node.operand)
def visit_unary_operation(self, op, operand) -> Iterable[str]:
yield op
yield SYMBOLS[type(op)]
yield from self.prec("unary").visit(operand)
def visit_IfExp(self, node: ast.IfExp) -> Iterable[str]:
......
......@@ -24,6 +24,6 @@ class FileVisitor(BlockVisitor):
yield from code
yield "}"
yield "int main(int argc, char* argv[]) {"
yield "py_sys::all.argv = PyList<PyStr>(std::vector<PyStr>(argv, argv + argc));"
yield "py_sys::all.argv = typon::PyList<PyStr>(std::vector<PyStr>(argv, argv + argc));"
yield "PROGRAMNS::root().call();"
yield "}"
......@@ -11,6 +11,7 @@ class SearchVisitor(NodeVisitor):
for val in node.__dict__.values():
if isinstance(val, list):
for item in val:
if isinstance(val, ast.AST):
yield from self.visit(item)
elif isinstance(val, ast.AST):
yield from self.visit(val)
......
......@@ -83,7 +83,9 @@ class ScoperBlockVisitor(ScoperVisitor):
raise NotImplementedError(node)
target = node.targets[0]
ty = self.get_type(node.value)
node.is_declare = self.visit_assign_target(target, ty)
decl = self.visit_assign_target(target, ty)
if not hasattr(node, "is_declare"):
node.is_declare = decl
def visit_AnnAssign(self, node: ast.AnnAssign):
# if node.value is not None:
......@@ -93,7 +95,9 @@ class ScoperBlockVisitor(ScoperVisitor):
if not isinstance(node.target, ast.Name):
raise NotImplementedError(node)
ty = self.visit_annotation(node.annotation)
node.is_declare = self.visit_assign_target(node.target, ty)
decl = self.visit_assign_target(node.target, ty)
if not hasattr(node, "is_declare"):
node.is_declare = decl
if node.value is not None:
ty_val = self.get_type(node.value)
TB = f"unifying annotation {highlight(node.annotation)} with value {highlight(node.value)} of type {highlight(ty_val)}"
......@@ -121,8 +125,9 @@ class ScoperBlockVisitor(ScoperVisitor):
if len(target.elts) != len(decl_val.args):
from transpiler.phases.typing.exceptions import InvalidUnpackCountError
raise InvalidUnpackCountError(decl_val, len(target.elts))
target.type = decl_val
decls = [self.visit_assign_target(t, ty) for t, ty in zip(target.elts, decl_val.args)] # eager evaluated
return any(decls)
return decls
elif isinstance(target, ast.Attribute):
attr_type = self.expr().visit(target)
attr_type.unify(decl_val)
......
......@@ -51,7 +51,7 @@ class StdlibVisitor(NodeVisitorSeq):
else:
class BuiltinClassType(TypeOperator):
def __init__(self, *args):
super().__init__(args, node.name)
super().__init__(args, node.name, is_reference=True)
ty = TypeType(BuiltinClassType)
self.scope.vars[node.name] = VarDecl(VarKind.LOCAL, ty)
typevars = []
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment