Boost.Beast state of play
Dear all, As you know, Boost.Beast has a strong dependency on Boost.Asio. At the present time, Chris is working to finalise some significant changes to Asio. These changes have required some refactoring of Boost.Beast at short notice in order to continue to provide a functioning library. Boost.Asio has two significant customisation macros: BOOST_ASIO_NO_DEPRECATED and BOOST_ASIO_NO_TS_EXECTORS. The 1.74 release of Asio deprecates some classes and interfaces relevant to net.ts-style executors. In addition, it introduces execution-style executors. *There is no combination of the above flags (save for none of them) that will allow an unmodified dependent library or program to compile as of boost.asio 1.74.* As of this moment, Beast is correctly compiling all examples and passing all tests with the exception of tests relevant to c++20 coroutines, where the latest Asio commit on develop branch has one (it would appear) remaining bug. Chris has been contacted and we are awaiting a fix. Once I have this, I will be in a position to rebase Beast PR1999 onto develop/master in readiness for the 1.74. Thank you for bearing with me during my time as an unwilling hostage to fortune. -- Richard Hodges hodges.r@gmail.com office: +442032898513 home: +376841522 mobile: +376380212
On Thu, 2 Jul 2020 at 16:21, Richard Hodges via Boost
At the present time, Chris is working to finalise some significant changes to Asio. These changes have required some refactoring of Boost.Beast at short notice in order to continue to provide a functioning library.
I don't think those changes should be rushed. If Boost.Asio is causing breakage across other Boost libraries, then the best thing to do is to delay the Boost.Asio changes. Also if Boost.Beast is broken, there are chances other users outside of Boost will be broken as well, so maybe something to consider?
On Thu, Jul 2, 2020 at 8:45 AM Mathias Gaunard via Boost
I don't think those changes should be rushed. If Boost.Asio is causing breakage across other Boost libraries, then the best thing to do is to delay the Boost.Asio changes.
For political reasons related to wg21 it is very important that Beast support these changes in THIS release. It will be of great value in helping to ensure that the design of Networking TS is tinkered with only a little bit in LEWG's hands rather than a lot (although anything can happen). The literal future of C++ networking is at stake. Thanks
On Thu, 2 Jul 2020, 17:01 Vinnie Falco,
On Thu, Jul 2, 2020 at 8:45 AM Mathias Gaunard via Boost
wrote: I don't think those changes should be rushed. If Boost.Asio is causing breakage across other Boost libraries, then the best thing to do is to delay the Boost.Asio changes.
For political reasons related to wg21 it is very important that Beast support these changes in THIS release. It will be of great value in helping to ensure that the design of Networking TS is tinkered with only a little bit in LEWG's hands rather than a lot (although anything can happen). The literal future of C++ networking is at stake.
I personally don't understand why people care about the C++ standard library at all, functionality can just as easily (if not more easily) be imported from third party libraries, and I'd rather trust a third party library written by a domain expert than a standard implementation written by a "language" expert. Also the quality of Boost is so variable -- some libraries are quite low quality and unmaintained -- that being part of Boost shouldn't be much of an argument to LEWG. Finally Asio being touted as the future of C++ networking when it's an old and established paradigm, possibly already behind as far as bleeding edge tech is concerned, might also suggest you're giving too much credit to the influence of the C++ standard library. I don't think standard Asio is going to change how anybody writes code. For those reasons I think C++ developers would be best served by delivering a quality and stable library in Boost than by trying to get stuff ready in time to appeal to a committee. That being said, from the rest of the replies it looks like you might be able to reconcile the two, so it's alright.
Copied here as I incorrectly replied direct.
On Thu, 2 Jul 2020 at 17:39, Mathias Gaunard
On Thu, 2 Jul 2020 at 16:21, Richard Hodges via Boost
wrote: At the present time, Chris is working to finalise some significant changes to Asio. These changes have required some refactoring of Boost.Beast at short notice in order to continue to provide a functioning library.
I don't think those changes should be rushed. If Boost.Asio is causing breakage across other Boost libraries, then the best thing to do is to delay the Boost.Asio changes.
Users of existing (1.73) Asio can avoid breakage with asio-only programs by not defining the macro BOOST_ASIO_NO_DEPRECATED
Also if Boost.Beast is broken, there are chances other users outside of Boost will be broken as well, so maybe something to consider?
In Beast we make a point of ensuring that Beast will function when
BOOST_ASIO_NO_DEPRECATED is defined so as not to unnecessarily restrict
user's code.
Furthermore this time around we are faced with a new macro
BOOST_BEAST_NO_TS_EXECUTORS, which completely removes the executors that
were introduced as recently as Boost 1.70.
Again, we feel obligated to ensure that user code compiles and functions
correctly if this macro is defined.
This is only my second Boost release, but I am given to understand that
last-minute rewrites of Asio are not unusual. Chris has been as helpful as
the 12-hour time-zone difference has allowed. We have been feeding back
test results and receiving updates for the past week.
I have no doubt that he will prevail, at least insofar as fixing the one
last minor bug that is blocking us in the c++20 build.
Once again, thanks for everyone's patience.
"I picked the wrong week to stop sniffing glue"
*- Airplane!*
On Thu, 2 Jul 2020 at 17:39, Mathias Gaunard
On Thu, 2 Jul 2020 at 16:21, Richard Hodges via Boost
wrote: At the present time, Chris is working to finalise some significant changes to Asio. These changes have required some refactoring of Boost.Beast at short notice in order to continue to provide a functioning library.
I don't think those changes should be rushed. If Boost.Asio is causing breakage across other Boost libraries, then the best thing to do is to delay the Boost.Asio changes.
Also if Boost.Beast is broken, there are chances other users outside of Boost will be broken as well, so maybe something to consider?
-- Richard Hodges hodges.r@gmail.com office: +442032898513 home: +376841522 mobile: +376380212
On 7/2/20 8:38 AM, Mathias Gaunard via Boost wrote:
On Thu, 2 Jul 2020 at 16:21, Richard Hodges via Boost
wrote: At the present time, Chris is working to finalise some significant changes to Asio. These changes have required some refactoring of Boost.Beast at short notice in order to continue to provide a functioning library.
I don't think those changes should be rushed. If Boost.Asio is causing breakage across other Boost libraries, then the best thing to do is to delay the Boost.Asio changes.
I agree with this. We have a good mechanism for handling this. The ASIO changes can go into the develop branch. Matching beast changes can go there as well. Then everthing can be tested/fixed without time constraints. When, when only when, things are fine on the develop branch, changes can be merged all at once to master. This will mean that users will be 3 months behind the bleeding edge. In my opinion, this is not a bad place to be.
Also if Boost.Beast is broken, there are chances other users outside of Boost will be broken as well, so maybe something to consider?
Right, and working under this sort of pressure, it seems pretty likely that something will be broken. Robert Ramey
On Thu, Jul 2, 2020 at 11:28 AM Robert Ramey via Boost
I agree with this.
That's very nice but worth precisely nothing, because you have no skin in the game at all. A delay means that for the next four months of SG4 Networking meetings we will have no field experience or knowledge to use to negate bad ideas that are brought before the committee. It is worth the risk. Thanks
On Thu, 2 Jul 2020 at 21:39, Vinnie Falco via Boost
On Thu, Jul 2, 2020 at 11:28 AM Robert Ramey via Boost
wrote: I agree with this.
That's very nice but worth precisely nothing, because you have no skin in the game at all. A delay means that for the next four months of SG4 Networking meetings we will have no field experience or knowledge to use to negate bad ideas that are brought before the committee. It is worth the risk.
While I understand your concern 110% (i.e. better than you do), the "WG21 politics" as you call them do not constitute a reason to release a possibly low-quality boost. You can appeal to existing implementation experience until the cows come home, but that alone doesn't guarantee that LEWG and WG21 end up standardizing an existing API without modifying it. Getting into such hypothetical plays is not worth the aforementioned possibly-lower release quality in boost. Boost should do what's technically and quality-wise right for Boost users. The WG21 part of it is someone else's problem (including mine), and we don't need shenanigans to get WG21 to do what's technically right for standardized networking.
On Thu, Jul 2, 2020 at 11:50 AM Ville Voutilainen
110%
(Note that 112% is the correct number)
"WG21 politics" as you call them do not constitute a reason to release a possibly low-quality boost.
That is certainly true, but since Asio's changes are beyond my control it is important for Beast to be up-to-date with respect to those changes in the same release, not one release later.
You can appeal to existing implementation experience until the cows come home, but that alone doesn't guarantee that LEWG and WG21 end up standardizing an existing API without modifying it.
There is a certain principle of loyalty and professional respect at play here. Christopher Kohlhoff is working hard on his own personal time with no corporate sponsor to bring us sane, robust networking while also working full time to keep the lights on. As my co-workers and I are team players we support Chris 112% by making sure that Beast supports the changes in Asio as soon as possible. Beast has always supported the latest changes in Asio and will continue to do so. Thanks
-----Original Message----- From: Boost
On Behalf Of Vinnie Falco via Boost Sent: 2 July 2020 20:25 To: Ville Voutilainen Cc: Vinnie Falco ; boost@lists.boost.org List ; Robert Ramey Subject: Re: [boost] Boost.Beast state of play On Thu, Jul 2, 2020 at 11:50 AM Ville Voutilainen
wrote: 110%
(Note that 112% is the correct number)
"WG21 politics" as you call them do not constitute a reason to release a possibly low-quality boost.
That is certainly true, but since Asio's changes are beyond my control it is important for Beast to be up- to-date with respect to those changes in the same release, not one release later.
All Boost releases risk causing someone trouble (and one way or another most do). IMO Vinnie has made a good enough case for *this issue* on *this release*. Paul
On 2020-07-03 12:25, Paul A Bristow via Boost wrote:
-----Original Message----- From: Boost
On Behalf Of Vinnie Falco via Boost Sent: 2 July 2020 20:25 To: Ville Voutilainen Cc: Vinnie Falco ; boost@lists.boost.org List ; Robert Ramey Subject: Re: [boost] Boost.Beast state of play On Thu, Jul 2, 2020 at 11:50 AM Ville Voutilainen
wrote: 110%
(Note that 112% is the correct number)
"WG21 politics" as you call them do not constitute a reason to release a possibly low-quality boost.
That is certainly true, but since Asio's changes are beyond my control it is important for Beast to be up- to-date with respect to those changes in the same release, not one release later.
All Boost releases risk causing someone trouble (and one way or another most do).
IMO Vinnie has made a good enough case for *this issue* on *this release*.
Vinnie's case was "because of WG21 politics". This is not a valid reason to compromise Boost quality, I totally agree with Ville on this. I find it somewhat disturbing that maintainers of a popular Boost library find that acceptable. Boost users experience should have a priority over WG21. Richard, however, presented a different case, that is: - Only a single test case is broken in a single configuration. - The test uses modern C++ features, which are expected to be rather unstable at this point. - There is a high chance that Chris will fix the problem before the release. Also, if I'm not mistaken, in the previous Boost release Boost.Beast had a problem in the same area, so basically Boost.Beast is not worse than the previous release. This is a more compelling case. I'd like to ask Richard to let us know if and when this problem gets resolved.
On Fri, 3 Jul 2020 at 12:25, Andrey Semashev via Boost < boost@lists.boost.org> wrote:
On 2020-07-03 12:25, Paul A Bristow via Boost wrote:
-----Original Message----- From: Boost
On Behalf Of Vinnie Falco via Boost
Sent: 2 July 2020 20:25 To: Ville Voutilainen
Cc: Vinnie Falco ; boost@lists.boost.org List < boost@lists.boost.org>; Robert Ramey Subject: Re: [boost] Boost.Beast state of play On Thu, Jul 2, 2020 at 11:50 AM Ville Voutilainen < ville.voutilainen@gmail.com> wrote:
110%
(Note that 112% is the correct number)
"WG21 politics" as you call them do not constitute a reason to release a possibly low-quality boost.
That is certainly true, but since Asio's changes are beyond my control it is important for Beast to be up- to-date with respect to those changes in the same release, not one release later.
All Boost releases risk causing someone trouble (and one way or another most do).
IMO Vinnie has made a good enough case for *this issue* on *this release*.
Vinnie's case was "because of WG21 politics". This is not a valid reason to compromise Boost quality, I totally agree with Ville on this. I find it somewhat disturbing that maintainers of a popular Boost library find that acceptable. Boost users experience should have a priority over WG21.
Richard, however, presented a different case, that is:
- Only a single test case is broken in a single configuration. - The test uses modern C++ features, which are expected to be rather unstable at this point. - There is a high chance that Chris will fix the problem before the release.
Also, if I'm not mistaken, in the previous Boost release Boost.Beast had a problem in the same area, so basically Boost.Beast is not worse than the previous release. This is a more compelling case. I'd like to ask Richard to let us know if and when this problem gets resolved.
Thanks for reaching out. Tests are all passing as of this morning. Because of the concern around stability I have increased the size of the test matrix that I run locally to test all legal combinations of compiler, c++ standard and preprocessor macro selections. (There’s no way this would complete in time with the free CI tools). Latest push of PR 1999 passes all tests with no regressions. I would expect to be merging onto master today once Vinnie has approved the documentation and release notes. Thank you everyone for you patience, and thanks also to Chris for responding so quickly to our exhaustive testing.
_______________________________________________ Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost
-- Richard Hodges hodges.r@gmail.com office: +442032898513 home: +376841522 mobile: +376380212
On Fri, 3 Jul 2020 at 20:25, Andrey Semashev via Boost
On 2020-07-03 12:25, Paul A Bristow via Boost wrote:
All Boost releases risk causing someone trouble (and one way or another most do).
IMO Vinnie has made a good enough case for *this issue* on *this release*.
Vinnie's case was "because of WG21 politics". This is not a valid reason to compromise Boost quality, I totally agree with Ville on this. I find it somewhat disturbing that maintainers of a popular Boost library find that acceptable. Boost users experience should have a priority over WG21.
Richard, however, presented a different case, that is:
- Only a single test case is broken in a single configuration. - The test uses modern C++ features, which are expected to be rather unstable at this point. - There is a high chance that Chris will fix the problem before the release.
And Chris presented the features available as a consequence of these
changes, and the options for users.
My comments below are as a user of asio and Beast (and a lot of other
Boost libraries - not all ones that have become or are likely to
become part of std::).
On Fri, 3 Jul 2020 at 11:11, Christopher Kohlhoff via Boost
1) BOOST_ASIO_NO_DEPRECATED
The handler invocation and allocation hooks were superseded and deprecated back in Boost 1.66, with the introduction of the networking TS compatibility:
https://www.boost.org/doc/libs/1_66_0/doc/html/boost_asio/net_ts.html
The only deprecation-related change for Asio in Boost 1.74 is that these hooks are now covered by BOOST_ASIO_NO_DEPRECATED. This will help users find and replace their usage of the hooks in their applications.
Beast changed to respect the definition of BOOST_ASIO_NO_DEPRECATED in relation to these hooks.
Nice. I like this so I can do that (find usage of deprecated hooks).
2) BOOST_ASIO_NO_TS_EXECUTORS
With Boost 1.74, Asio adds an implementation of the proposed C++23 standard executors. This is in addition to the existing executors implementation which is defined in the networking TS.
Most applications will require no modification, or very little. If absolutely necessary, users can define BOOST_ASIO_USE_TS_EXECUTOR_AS_DEFAULT to enable full backward compatibility.
Nice to know I can do this if I need to.
A user may choose to define BOOST_ASIO_NO_TS_EXECUTORS so that they can disable networking TS executors entirely, and use only the proposed C++23 executors. Even when this is defined, unless interacting directly with executors at a low level, most code will require little or no change.
I don't want to do that - yet. But it's a nice-to-have for when/if there is a C++23 executor impl I want to use (for me, no rush, and certainly not in prod code).
Beast changed as follows:
* To support the proposed C++23 standard executors implementation as an additive feature.
* To respect the user's definition of BOOST_ASIO_NO_TS_EXECUTORS.
Good to know that whatever pain this migration may entail, Beast has it covered and I can experiment not just with my code that uses asio but also in code that uses Beast.
The common theme here is that these changes impact Beast more than they will impact end users, because Beast opts to support and pass through Asio's latest features without attenuation. This allows Beast users to employ these latest features in their applications.
I'm really happy to see this approach. It seems to be exactly what Boost should be doing. As a Boost user, I won't update to the new Boost release in existing production code without careful consideration of any impacts. On the other hand, I will, in new or evolving code, be keen to use new features and stop using deprecated ones - the fact that I can do both using this release is ideal. This is a great example of effectively resolving the conflict between Boost as a distribution of high quality code one can depend on (in some cases for many years) when that code is not part of the standard (or the standard library being used) and also providing a whole environment that can evolve and test the fitness of both the existing (through adaptation) and then newcomer (through filling a niche in this ecosystem). This effort should be applauded - including the level of testing of new unusual configurations being performed. If only every library/product was as thorough. I don't see this as an indication of dropping the quality of the release at all.
Some nice highlights: 1. Richard did an incredible job in Beast to support these Asio changes, it looks like we have a very talented, competent, and motivated maintainer in the fold now! 2. Chris was very helpful in explaining and providing assistance with these changes. 3. Looks like the mailing lists got more interesting again :) Regards
On 03/07/2020 11:24, Andrey Semashev via Boost wrote:
Vinnie's case was "because of WG21 politics". This is not a valid reason to compromise Boost quality, I totally agree with Ville on this. I find it somewhat disturbing that maintainers of a popular Boost library find that acceptable. Boost users experience should have a priority over WG21.
It's funny how Boost.ASIO has suddenly gone from being a very, very conservative flavour of standalone ASIO, typically trailing by a few major versions, to where "the stable branch" is code literally written new in the last few weeks, and with a major rearchitecture to boot. In the end, each library maintainer gets to make that call for their own library. But I've always gotten the impression from others here that major new features should either get a mini review (unnecessary in this instance due to the WG21 review), or undergo at least a year of testing, and then ought to be preannounced by least two major Boost releases in advance before they get merged to master branch. As an example, I've just announced that Outcome will break all existing code in two Boost releases time in the Boost changelog. I have been announcing it on the front page since last Christmas. Now, little in latest Boost.ASIO will break existing code in obvious ways. But I have to believe that newly written code is usually more buggy and/or surprising than older code. It seems unusual to me to launch that onto users without notification. Again, if that maintainer doesn't mind the onslaught of bug reports, especially from downstream distros e.g. RHEL, Debian, StackOverflow, that's on them. I just find it masochistic, that's all. Niall
On 03/07/2020 16:56, Vinnie Falco wrote:
On Fri, Jul 3, 2020 at 6:55 AM Niall Douglas via Boost
wrote: ...Outcome will break all existing code...
Chris K: "Asio is getting some API changes this release" Beast: "Beast is tracking Asio's API changes this release" Niall: "Hold my beer..."
The upgrade path from Outcome v2.1 to v2.2 is well documented. Lots of production codebases have been on v2.2 for many months now, including my work's. Converting over the codebase took less than 15 minutes if you follow the guide. A full calender year of notice has been given that this is coming. And moreover, it was always made clear from the beginning that we would do at least one big breaking API change before we go permanently ABI stable, for which it is extremely important we never ever change much of anything ever again thereafter. Niall
Niall Douglas wrote:
It's funny how Boost.ASIO has suddenly gone from being a very, very conservative flavour of standalone ASIO, typically trailing by a few major versions, to where "the stable branch" is code literally written new in the last few weeks, and with a major rearchitecture to boot.
In the end, each library maintainer gets to make that call for their own library.
In principle we have a three-tiered procedure of rolling out API changes: 1. Update develop This gets feedback from other Boost library developers who depend on the API and test against the develop branch. 2. Update master This is supposed to get feedback from outside users who track master in order to not be surprised by the release, but in practice, no such people seem to exist, so it mostly gets feedback from Boost library developers who erroneously test against master. 3. Get a release out This gets feedback from everyone else. Theoretically, (1) should happen at some point during release cycle N-1, (2) happens in the beginning of release cycle N, and (3) happens at the end of release cycle N. In practice though, not much is gained by spreading them out. Most of the world doesn't care unless changes go out in a release. I'd still call the above schedule "best practice" though; or if not that, its compressed form where (1) is at beginning of N, (2) is in the middle.
On 7/3/20 9:45 AM, Peter Dimov via Boost wrote: ...
2. Update master
This is supposed to get feedback from outside users who track master in order to not be surprised by the release, but in practice, no such people seem to exist, so it mostly gets feedback from Boost library developers who erroneously test against master.
LOL erroneously? - one is allowed to name names. As one who tests against master for reasons I've specified elsewhere, I should say: a) I almost never find bugs/unannounced changes in the master API. b) But truth is, I generally pull from the master branch only when I'm about to check my own code into the master. So I'm not providing much feedback as things mostly work by the time they get checked into the master.
I'd still call the above schedule "best practice" though; or if not that, its compressed form where (1) is at beginning of N, (2) is in the middle.
+1 The current setup works well and decouples one's development from the release schedule. We should continue to rely on that. Robert Ramey
Am 03.07.20 um 18:45 schrieb Peter Dimov via Boost:
2. Update master
This is supposed to get feedback from outside users who track master in order to not be surprised by the release, but in practice, no such people seem to exist, so it mostly gets feedback from Boost library developers who erroneously test against master.
Just as a clarification to not downplay this second step: On my library (and I suppose others are similar, at least when using Boost.CI) the master branch gets tested against the other libraries master branch. So when merging to master you'll get feedback from others with their respective master branches given their CI is rerun (on merge develop->master or on cron job) That's why I find the badges for develop and master CI in the Readme helpful and important as they also update on the "cron job" rerun on master. I'm not sure how often the Boost "super CI" testing the whole of Boost is run but that also has 1 configuration for master branches. So you can check there too.
On Fri, Jul 3, 2020 at 6:55 AM Niall Douglas via Boost
code literally written new in the last few weeks, and with a major rearchitecture to boot.
There's no "major rearchitecture" in this new version of Asio, it is just a refactoring and changing of spelling of the interfaces to executors. They still do the same things: * maybe track outstanding work * hint to the context that the submitted function object represents a continuation of a larger I/O operation * get the execution context from an executor * provide a polymorphic executor type Except that the incantations required of users is now different (net::require and net::prefer for example, are new ways to do old things). It is still the same Asio under the hood. None of the fundamental design is different, and most users won't notice these changes. Thanks
On Thu, 2 Jul 2020 at 20:28, Robert Ramey via Boost
that something will be broken.
I thought it worth mentioning that: * We are only one test failure away from a flawless (zero regression) test. * That failure only occurs in asio::co_spawn (c++20 coroutines) when BOOST_ASIO_NO_TS_EXECUTORS is defined. * Chris has been very responsive to our bug reports. * The bug is more of an oversight than a logic error. * Boost.Beast's test suite represents a very thorough workout of the Asio executor model, which is the element being updated in this release. I imagine this will be solved by tomorrow. It was not my intent to alarm the community, merely to keep everyone informed as to progress.
_______________________________________________ Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost
-- Richard Hodges hodges.r@gmail.com office: +442032898513 home: +376841522 mobile: +376380212
On Fri, Jul 3, 2020, at 1:21 AM, Richard Hodges via Boost wrote:
[...]
This post refers to unrelated things, so for clarity: 1) BOOST_ASIO_NO_DEPRECATED The handler invocation and allocation hooks were superseded and deprecated back in Boost 1.66, with the introduction of the networking TS compatibility: https://www.boost.org/doc/libs/1_66_0/doc/html/boost_asio/net_ts.html The only deprecation-related change for Asio in Boost 1.74 is that these hooks are now covered by BOOST_ASIO_NO_DEPRECATED. This will help users find and replace their usage of the hooks in their applications. Beast changed to respect the definition of BOOST_ASIO_NO_DEPRECATED in relation to these hooks. 2) BOOST_ASIO_NO_TS_EXECUTORS With Boost 1.74, Asio adds an implementation of the proposed C++23 standard executors. This is in addition to the existing executors implementation which is defined in the networking TS. Most applications will require no modification, or very little. If absolutely necessary, users can define BOOST_ASIO_USE_TS_EXECUTOR_AS_DEFAULT to enable full backward compatibility. A user may choose to define BOOST_ASIO_NO_TS_EXECUTORS so that they can disable networking TS executors entirely, and use only the proposed C++23 executors. Even when this is defined, unless interacting directly with executors at a low level, most code will require little or no change. Beast changed as follows: * To support the proposed C++23 standard executors implementation as an additive feature. * To respect the user's definition of BOOST_ASIO_NO_TS_EXECUTORS. The common theme here is that these changes impact Beast more than they will impact end users, because Beast opts to support and pass through Asio's latest features without attenuation. This allows Beast users to employ these latest features in their applications. The majority of users, and especially those that define neither of the above preprocessor macros, should experience little or no change.
participants (12)
-
Alexander Grund
-
Andrey Semashev
-
Christopher Kohlhoff
-
Darryl Green
-
Mathias Gaunard
-
Niall Douglas
-
pbristow@hetp.u-net.com
-
Peter Dimov
-
Richard Hodges
-
Robert Ramey
-
Ville Voutilainen
-
Vinnie Falco