diff --git a/direct/src/dist/commands.py b/direct/src/dist/commands.py index b70effdf87..644b3774c6 100644 --- a/direct/src/dist/commands.py +++ b/direct/src/dist/commands.py @@ -396,27 +396,22 @@ class build_apps(setuptools.Command): self.announce('Gathering wheels for platform: {}'.format(platform), distutils.log.INFO) - whldir = os.path.join(self.build_base, '__whl_cache__') + whlcache = os.path.join(self.build_base, '__whl_cache__') - #TODO find a better way to get abi tag than from internal/private pip APIs - if hasattr(pip, 'pep425tags'): - pep425tags = pip.pep425tags - wheel = pip.wheel - else: - from pip._internal import pep425tags, wheel + pip_version = int(pip.__version__.split('.')[0]) + if pip_version < 9: + raise RuntimeError("pip 9.0 or greater is required, but found {}".format(pip.__version__)) - abi_tag = pep425tags.get_abi_tag() - - if 'u' in abi_tag and (platform.startswith('win') or platform.startswith('macosx')): - abi_tag = abi_tag.replace('u', '') + abi_tag = 'cp%d%d' % (sys.version_info[:2]) + if sys.version_info < (3, 8): + abi_tag += 'm' # For these distributions, we need to append 'u' on Linux if abi_tag in ('cp26m', 'cp27m', 'cp32m') and not platform.startswith('win') and not platform.startswith('macosx'): abi_tag += 'u' - pip_version = pip.__version__.split('.') - if int(pip_version[0]) < 9: - raise RuntimeError("pip 9.0 or greater is required, but found {}".format(pip.__version__)) + whldir = os.path.join(whlcache, '_'.join((platform, abi_tag))) + os.makedirs(whldir, exist_ok=True) # Remove any .zip files. These are built from a VCS and block for an # interactive prompt on subsequent downloads. @@ -444,19 +439,12 @@ class build_apps(setuptools.Command): subprocess.check_call([sys.executable, '-m', 'pip'] + pip_args) - # Now figure out which of the downloaded wheels are relevant to us. - tags = pep425tags.get_supported(platform=platform, abi=abi_tag) - wheelpaths = [] - for filename in os.listdir(whldir): - try: - whl = wheel.Wheel(filename) - except wheel.InvalidWheelFilename: - continue - - if whl.supported(tags): - wheelpaths.append(os.path.join(whldir, filename)) - - return wheelpaths + # Return a list of paths to the downloaded whls + return [ + os.path.join(whldir, filename) + for filename in os.listdir(whldir) + if filename.endswith('.whl') + ] def update_pe_resources(self, appname, runtime): """Update resources (e.g., icons) in windows PE file""" diff --git a/dtool/src/dtoolutil/win32ArgParser.cxx b/dtool/src/dtoolutil/win32ArgParser.cxx index 4faf6bff95..81fb6ba7e9 100644 --- a/dtool/src/dtoolutil/win32ArgParser.cxx +++ b/dtool/src/dtoolutil/win32ArgParser.cxx @@ -22,7 +22,7 @@ #include "executionEnvironment.h" #include -#include +#include using std::string; diff --git a/dtool/src/interrogate/typeManager.cxx b/dtool/src/interrogate/typeManager.cxx index ab1fbffce3..dba10f4520 100644 --- a/dtool/src/interrogate/typeManager.cxx +++ b/dtool/src/interrogate/typeManager.cxx @@ -1442,7 +1442,7 @@ is_void(CPPType *type) { /** * Returns true if the indicated type is some class that derives from - * ReferenceCount, or false otherwise. + * ReferenceCount, or defines ref and unref(), or false otherwise. */ bool TypeManager:: is_reference_count(CPPType *type) { @@ -1459,6 +1459,14 @@ is_reference_count(CPPType *type) { case CPPDeclaration::ST_struct: { CPPStructType *stype = type->as_struct_type(); + + // If we have methods named ref() and unref(), this is good enough. + if (stype->_scope->_functions.count("ref") && + stype->_scope->_functions.count("unref") && + stype->_scope->_functions.count("get_ref_count")) { + return true; + } + CPPStructType::Derivation::const_iterator di; for (di = stype->_derivation.begin(); di != stype->_derivation.end(); diff --git a/makepanda/makepanda.py b/makepanda/makepanda.py index 2c5a369606..8e88a40930 100755 --- a/makepanda/makepanda.py +++ b/makepanda/makepanda.py @@ -397,6 +397,20 @@ elif target == 'linux' and (os.path.isfile("/lib/libc-2.5.so") or os.path.isfile else: PLATFORM = 'manylinux1-i686' +elif target == 'linux' and (os.path.isfile("/lib/libc-2.12.so") or os.path.isfile("/lib64/libc-2.12.so")) and os.path.isdir("/opt/python"): + # Same sloppy check for manylinux2010. + if GetTargetArch() in ('x86_64', 'amd64'): + PLATFORM = 'manylinux2010-x86_64' + else: + PLATFORM = 'manylinux2010-i686' + +elif target == 'linux' and (os.path.isfile("/lib/libc-2.17.so") or os.path.isfile("/lib64/libc-2.17.so")) and os.path.isdir("/opt/python"): + # Same sloppy check for manylinux2014. + if GetTargetArch() in ('x86_64', 'amd64'): + PLATFORM = 'manylinux2014-x86_64' + else: + PLATFORM = 'manylinux2014-i686' + elif not CrossCompiling(): if HasTargetArch(): # Replace the architecture in the platform string. diff --git a/makepanda/makewheel.py b/makepanda/makewheel.py index f1129a133d..a62417588f 100644 --- a/makepanda/makewheel.py +++ b/makepanda/makewheel.py @@ -92,7 +92,7 @@ EXCLUDE_EXT = [".pyc", ".pyo", ".N", ".prebuilt", ".xcf", ".plist", ".vcproj", " # Plug-ins to install. PLUGIN_LIBS = ["pandagl", "pandagles", "pandagles2", "pandadx9", "p3tinydisplay", "p3ptloader", "p3assimp", "p3ffmpeg", "p3openal_audio", "p3fmod_audio"] -# Libraries included in manylinux ABI that should be ignored. See PEP 513/571. +# Libraries included in manylinux ABI that should be ignored. See PEP 513/571/599. MANYLINUX_LIBS = [ "libgcc_s.so.1", "libstdc++.so.6", "libm.so.6", "libdl.so.2", "librt.so.1", "libcrypt.so.1", "libc.so.6", "libnsl.so.1", "libutil.so.1", @@ -530,10 +530,14 @@ def makewheel(version, output_dir, platform=None): else: print("Could not find platform.dat in build directory") platform = get_platform() - if platform.startswith("linux-"): - # Is this manylinux1? - if os.path.isfile("/lib/libc-2.5.so") and os.path.isdir("/opt/python"): + if platform.startswith("linux-") and os.path.isdir("/opt/python"): + # Is this manylinux? + if os.path.isfile("/lib/libc-2.5.so") or os.path.isfile("/lib64/libc-2.5.so"): platform = platform.replace("linux", "manylinux1") + elif os.path.isfile("/lib/libc-2.12.so") or os.path.isfile("/lib64/libc-2.12.so"): + platform = platform.replace("linux", "manylinux2010") + elif os.path.isfile("/lib/libc-2.17.so") or os.path.isfile("/lib64/libc-2.17.so"): + platform = platform.replace("linux", "manylinux2014") platform = platform.replace('-', '_').replace('.', '_') @@ -735,7 +739,12 @@ if __debug__: pylib_path = os.path.join(get_config_var('LIBDIR'), pylib_name) else: pylib_name = get_config_var('LDLIBRARY') - pylib_path = os.path.join(get_config_var('LIBDIR'), pylib_name) + pylib_arch = get_config_var('MULTIARCH') + libdir = get_config_var('LIBDIR') + if pylib_arch and os.path.exists(os.path.join(libdir, pylib_arch, pylib_name)): + pylib_path = os.path.join(libdir, pylib_arch, pylib_name) + else: + pylib_path = os.path.join(libdir, pylib_name) whl.write_file('deploy_libs/' + pylib_name, pylib_path) whl.close() diff --git a/panda/src/device/winInputDeviceManager.h b/panda/src/device/winInputDeviceManager.h index 13cab3d7c0..e98a42a0bb 100644 --- a/panda/src/device/winInputDeviceManager.h +++ b/panda/src/device/winInputDeviceManager.h @@ -20,7 +20,7 @@ #include "xInputDevice.h" -#include +#include #include class WinRawInputDevice; diff --git a/panda/src/device/winRawInputDevice.cxx b/panda/src/device/winRawInputDevice.cxx index 9411ad508b..010766edf0 100644 --- a/panda/src/device/winRawInputDevice.cxx +++ b/panda/src/device/winRawInputDevice.cxx @@ -19,7 +19,7 @@ #if defined(_WIN32) && !defined(CPPPARSER) -#include +#include #include #include "phidsdi.h" diff --git a/panda/src/device/xInputDevice.cxx b/panda/src/device/xInputDevice.cxx index 74783f8751..bcc44cd3b1 100644 --- a/panda/src/device/xInputDevice.cxx +++ b/panda/src/device/xInputDevice.cxx @@ -19,8 +19,8 @@ #include "inputDeviceManager.h" #include "string_utils.h" -#include -#include +#include +#include #ifndef XUSER_MAX_COUNT #define XUSER_MAX_COUNT 4 diff --git a/panda/src/device/xInputDevice.h b/panda/src/device/xInputDevice.h index 2088c19182..c4a1f58d27 100644 --- a/panda/src/device/xInputDevice.h +++ b/panda/src/device/xInputDevice.h @@ -19,7 +19,7 @@ #if defined(_WIN32) && !defined(CPPPARSER) -#include +#include class InputDeviceManager; diff --git a/panda/src/display/graphicsEngine.cxx b/panda/src/display/graphicsEngine.cxx index 287eb8eeb5..9843f818ba 100644 --- a/panda/src/display/graphicsEngine.cxx +++ b/panda/src/display/graphicsEngine.cxx @@ -56,7 +56,7 @@ #if defined(_WIN32) #define WINDOWS_LEAN_AND_MEAN - #include + #include #include #undef WINDOWS_LEAN_AND_MEAN #else diff --git a/panda/src/downloader/bioStreamBuf.cxx b/panda/src/downloader/bioStreamBuf.cxx index 93b22d9c93..ffa6a2994e 100644 --- a/panda/src/downloader/bioStreamBuf.cxx +++ b/panda/src/downloader/bioStreamBuf.cxx @@ -19,7 +19,7 @@ #ifdef HAVE_OPENSSL #ifdef _WIN32 - #include + #include #include // for WSAGetLastError() #undef X509_NAME #endif // _WIN32 diff --git a/panda/src/downloader/httpChannel.cxx b/panda/src/downloader/httpChannel.cxx index aa5880080a..f066b24943 100644 --- a/panda/src/downloader/httpChannel.cxx +++ b/panda/src/downloader/httpChannel.cxx @@ -30,7 +30,7 @@ #include "openSSLWrapper.h" #ifdef _WIN32 - #include + #include #include // for select() #undef X509_NAME #endif // _WIN32 diff --git a/panda/src/nativenet/socket_portable.h b/panda/src/nativenet/socket_portable.h index a4a249f92e..2ac1c89248 100644 --- a/panda/src/nativenet/socket_portable.h +++ b/panda/src/nativenet/socket_portable.h @@ -53,7 +53,7 @@ typedef unsigned long SOCKET; ************************************************************************/ #elif defined(_WIN32) #include -#include +#include typedef u_short sa_family_t; diff --git a/panda/src/net/connectionManager.cxx b/panda/src/net/connectionManager.cxx index af2efc5d25..1af31a8f78 100644 --- a/panda/src/net/connectionManager.cxx +++ b/panda/src/net/connectionManager.cxx @@ -25,7 +25,7 @@ #if defined(CPPPARSER) #elif defined(_WIN32) #include // For gethostname() -#include // For GetAdaptersAddresses() +#include // For GetAdaptersAddresses() #elif defined(__ANDROID__) #include #else diff --git a/panda/src/pgraph/cullableObject.cxx b/panda/src/pgraph/cullableObject.cxx index 920e524659..38f35f7024 100644 --- a/panda/src/pgraph/cullableObject.cxx +++ b/panda/src/pgraph/cullableObject.cxx @@ -223,29 +223,23 @@ munge_points_to_quads(const CullTraverser *traverser, bool force) { return false; } + GeomVertexDataPipelineReader reader(source_data, current_thread); + reader.check_array_readers(); + PStatTimer timer(_munge_sprites_pcollector, current_thread); - _sw_sprites_pcollector.add_level(source_data->get_num_rows()); + _sw_sprites_pcollector.add_level(reader.get_num_rows()); GraphicsStateGuardianBase *gsg = traverser->get_gsg(); - GeomVertexReader vertex(source_data, InternalName::get_vertex(), - current_thread); - GeomVertexReader normal(source_data, InternalName::get_normal(), - current_thread); - GeomVertexReader color(source_data, InternalName::get_color(), - current_thread); - GeomVertexReader texcoord(source_data, InternalName::get_texcoord(), - current_thread); - GeomVertexReader rotate(source_data, InternalName::get_rotate(), - current_thread); - GeomVertexReader size(source_data, InternalName::get_size(), - current_thread); - GeomVertexReader aspect_ratio(source_data, InternalName::get_aspect_ratio(), - current_thread); + GeomVertexReader vertex(&reader, InternalName::get_vertex()); + GeomVertexReader normal(&reader, InternalName::get_normal()); + GeomVertexReader rotate(&reader, InternalName::get_rotate()); + GeomVertexReader size(&reader, InternalName::get_size()); + GeomVertexReader aspect_ratio(&reader, InternalName::get_aspect_ratio()); bool has_normal = (normal.has_column()); - bool has_color = (color.has_column()); - bool has_texcoord = (texcoord.has_column()); + bool has_color = (reader.has_column(InternalName::get_color())); + bool has_texcoord = (reader.has_column(InternalName::get_texcoord())); bool has_rotate = (rotate.has_column()); bool has_size = (size.has_column()); bool has_aspect_ratio = (aspect_ratio.has_column()); @@ -280,7 +274,7 @@ munge_points_to_quads(const CullTraverser *traverser, bool force) { { LightMutexHolder holder(_format_lock); - SourceFormat sformat(source_data->get_format(), sprite_texcoord); + SourceFormat sformat(reader.get_format(), sprite_texcoord); FormatMap::iterator fmi = _format_map.find(sformat); if (fmi != _format_map.end()) { new_format = (*fmi).second; @@ -304,13 +298,13 @@ munge_points_to_quads(const CullTraverser *traverser, bool force) { Geom::C_clip_point); } if (has_normal) { - const GeomVertexColumn *c = normal.get_column(); + const GeomVertexColumn *c = reader.get_format()->get_normal_column(); new_array_format->add_column (InternalName::get_normal(), c->get_num_components(), c->get_numeric_type(), c->get_contents()); } if (has_color) { - const GeomVertexColumn *c = color.get_column(); + const GeomVertexColumn *c = reader.get_format()->get_color_column(); new_array_format->add_column (InternalName::get_color(), c->get_num_components(), c->get_numeric_type(), c->get_contents()); @@ -322,12 +316,34 @@ munge_points_to_quads(const CullTraverser *traverser, bool force) { Geom::C_texcoord); } else if (has_texcoord) { - const GeomVertexColumn *c = texcoord.get_column(); + const GeomVertexColumn *c = reader.get_format()->get_column(InternalName::get_texcoord()); new_array_format->add_column (InternalName::get_texcoord(), c->get_num_components(), c->get_numeric_type(), c->get_contents()); } + // Go through the other columns and copy them from the original. + for (size_t ai = 0; ai < sformat._format->get_num_arrays(); ++ai) { + const GeomVertexArrayFormat *aformat = sformat._format->get_array(ai); + + for (size_t ci = 0; ci < aformat->get_num_columns(); ++ci) { + const GeomVertexColumn *column = aformat->get_column(ci); + const InternalName *name = column->get_name(); + if (name != InternalName::get_vertex() && + name != InternalName::get_normal() && + name != InternalName::get_color() && + name != InternalName::get_texcoord() && + name != InternalName::get_rotate() && + name != InternalName::get_size() && + name != InternalName::get_aspect_ratio()) { + + new_array_format->add_column(name, + column->get_num_components(), column->get_numeric_type(), + column->get_contents()); + } + } + } + new_format = GeomVertexFormat::register_format(new_array_format); _format_map[sformat] = new_format; } @@ -362,7 +378,7 @@ munge_points_to_quads(const CullTraverser *traverser, bool force) { // Now convert all of the vertices in the GeomVertexData to quads. We // always convert all the vertices, assuming all the vertices are referenced // by GeomPrimitives, because we want to optimize for the most common case. - int orig_verts = source_data->get_num_rows(); + int orig_verts = reader.get_num_rows(); int new_verts = 4 * orig_verts; // each vertex becomes four. PT(GeomVertexData) new_data = new GeomVertexData @@ -371,9 +387,50 @@ munge_points_to_quads(const CullTraverser *traverser, bool force) { GeomVertexWriter new_vertex(new_data, InternalName::get_vertex()); GeomVertexWriter new_normal(new_data, InternalName::get_normal()); - GeomVertexWriter new_color(new_data, InternalName::get_color()); GeomVertexWriter new_texcoord(new_data, InternalName::get_texcoord()); + nassertr(new_vertex.has_column(), false); + unsigned char *write_ptr = new_vertex.get_array_handle()->get_write_pointer(); + + // Collect all other columns that we just need to copy the data of. + struct CopyOp { + unsigned char *_to_pointer; + const unsigned char *_from_pointer; + size_t _num_bytes; + size_t _from_stride; + }; + pvector copies; + + const GeomVertexArrayFormat *aformat = new_format->get_array(0); + for (size_t ci = 0; ci < aformat->get_num_columns(); ++ci) { + const GeomVertexColumn *column = aformat->get_column(ci); + const InternalName *name = column->get_name(); + if (name != InternalName::get_vertex() && + (retransform_sprites || name != InternalName::get_normal()) && + (!sprite_texcoord || name != InternalName::get_texcoord())) { + + int source_array; + const GeomVertexColumn *source_column; + if (reader.get_format()->get_array_info(name, source_array, source_column)) { + CopyOp copy; + copy._to_pointer = write_ptr + (size_t)column->get_start(); + copy._from_pointer = reader.get_array_reader(source_array)->get_read_pointer(true) + (size_t)source_column->get_start(); + copy._num_bytes = (size_t)column->get_total_bytes(); + copy._from_stride = reader.get_format()->get_array(source_array)->get_stride(); + + if (!copies.empty() && + (copy._to_pointer == copies.back()._to_pointer + copies.back()._num_bytes) && + (copy._from_pointer == copies.back()._from_pointer + copies.back()._num_bytes)) { + // Merge with previous. + copies.back()._num_bytes += copy._num_bytes; + } else { + copies.push_back(copy); + } + } + } + } + size_t to_stride = aformat->get_stride(); + // We'll keep an array of all of the points' eye-space coordinates, and // their distance from the camera, so we can sort the points for each // primitive, below. @@ -447,14 +504,6 @@ munge_points_to_quads(const CullTraverser *traverser, bool force) { new_vertex.set_data4(inv_render_transform.xform(LPoint4(p4[0] - c1[0], p4[1] - c1[1], p4[2], p4[3]))); new_vertex.set_data4(inv_render_transform.xform(LPoint4(p4[0] - c0[0], p4[1] - c0[1], p4[2], p4[3]))); - if (has_normal) { - const LNormal &c = normal.get_data3(); - new_normal.set_data3(c); - new_normal.set_data3(c); - new_normal.set_data3(c); - new_normal.set_data3(c); - } - } else { // Without retransform_sprites, we can simply load the clip-space // coordinates. @@ -464,6 +513,7 @@ munge_points_to_quads(const CullTraverser *traverser, bool force) { new_vertex.set_data4(p4[0] - c0[0], p4[1] - c0[1], p4[2], p4[3]); if (has_normal) { + // We need to transform the normals to clip-space too, then. LNormal c = render_transform.xform_vec(normal.get_data3()); new_normal.set_data3(c); new_normal.set_data3(c); @@ -471,24 +521,24 @@ munge_points_to_quads(const CullTraverser *traverser, bool force) { new_normal.set_data3(c); } } - if (has_color) { - const LColor &c = color.get_data4(); - new_color.set_data4(c); - new_color.set_data4(c); - new_color.set_data4(c); - new_color.set_data4(c); - } if (sprite_texcoord) { new_texcoord.set_data2(1.0f, 0.0f); new_texcoord.set_data2(0.0f, 0.0f); new_texcoord.set_data2(1.0f, 1.0f); new_texcoord.set_data2(0.0f, 1.0f); - } else if (has_texcoord) { - const LVecBase4 &c = texcoord.get_data4(); - new_texcoord.set_data4(c); - new_texcoord.set_data4(c); - new_texcoord.set_data4(c); - new_texcoord.set_data4(c); + } + + // Other columns are simply duplicated for each vertex. + for (CopyOp © : copies) { + memcpy(copy._to_pointer, copy._from_pointer, copy._num_bytes); + copy._to_pointer += to_stride; + memcpy(copy._to_pointer, copy._from_pointer, copy._num_bytes); + copy._to_pointer += to_stride; + memcpy(copy._to_pointer, copy._from_pointer, copy._num_bytes); + copy._to_pointer += to_stride; + memcpy(copy._to_pointer, copy._from_pointer, copy._num_bytes); + copy._to_pointer += to_stride; + copy._from_pointer += copy._from_stride; } ++vi; diff --git a/panda/src/pstatclient/pStatClientImpl.cxx b/panda/src/pstatclient/pStatClientImpl.cxx index 3d6973259a..f25b863b97 100644 --- a/panda/src/pstatclient/pStatClientImpl.cxx +++ b/panda/src/pstatclient/pStatClientImpl.cxx @@ -28,7 +28,7 @@ #include #ifdef _WIN32 -#include +#include #include #endif diff --git a/panda/src/x11display/x11GraphicsWindow.cxx b/panda/src/x11display/x11GraphicsWindow.cxx index 6ba210bc1f..c7d3455164 100644 --- a/panda/src/x11display/x11GraphicsWindow.cxx +++ b/panda/src/x11display/x11GraphicsWindow.cxx @@ -2038,6 +2038,13 @@ get_keyboard_map() const { LightReMutexHolder holder(x11GraphicsPipe::_x_mutex); for (int k = 9; k <= 135; ++k) { + if (k >= 78 && k <= 91) { + // Ignore numpad keys for now. These are not mapped to separate button + // handles in Panda, so we don't want their mappings to conflict with + // the regular numeric keys. + continue; + } + ButtonHandle raw_button = map_raw_button(k); if (raw_button == ButtonHandle::none()) { continue; @@ -2045,11 +2052,31 @@ get_keyboard_map() const { KeySym sym = XkbKeycodeToKeysym(_display, k, 0, 0); ButtonHandle button = map_button(sym); - if (button == ButtonHandle::none()) { + std::string label; + + // Compose a label for some keys; I have not yet been able to find an API + // that does this effectively. + if (sym >= XK_a && sym <= XK_z) { + label = toupper((char)sym); + } + else if (sym >= XK_F1 && sym <= XK_F35) { + label = "F" + format_string(sym - XK_F1 + 1); + } + else if (sym >= XK_exclamdown && sym <= XK_ydiaeresis) { + // A latin-1 symbol. Translate this to the label. + char buffer[255]; + int nbytes = XkbTranslateKeySym(_display, &sym, 0, buffer, 255, 0); + if (nbytes > 0) { + label.assign(buffer, nbytes); + } + } + + if (button == ButtonHandle::none() && label.empty()) { + // No label and no mapping; this is useless. continue; } - map->map_button(raw_button, button); + map->map_button(raw_button, button, label); } return map;