Hey,

> Finally, I produced these branches by running git-svn and git-filter-
> branch against our internal SVN repositories.  The addition of the
> root "src" directory and the lack of a clear branch from 1.2.3 make
> comparison with existing branches unnecessarily difficult.  I
> apologize for the inconvenience.  I will redo the git svn extraction
> to correct those issues later this week.

Thank you for the clarification. Though that's similar to what our own git
repo was until dustin rewrote it, and what mine presently is.

What we have right now are actually three trees with unrelated history.
Mine - the original cleaned up git-svn import. Dustin's, the rewritten
binary tree, and now FB's, which is a weird rewrite based off of 1.2.3.

So right now I have all the benefits of a nice distributed RCS, but none
of the benefits of being able to manage these branches, since we're all
touting to have the same thing with unrelated histories. My work in the
short term is to get the binary and stable trees related again, since even
if the binary protocol goes out, we will have to maintain the 1.2 series
for a while.

> In the mean time I hope you will let us know what you think and what
> else we can do to make memcached even better.  We at facebook would be
> happy to discuss questions and issues about our release in this group.

Sounds good. I'll reiterate the things we've gone over privately
already and we'll work from there.

First, for clarity, a few small bits that were discernable from the last
merge request were committed and credited in the stable tree. I don't
think that's been in a release yet, however. Apologies on my part.

As Dustin said, the facebook tree, in its current state, is basically
unmergable. For the handful of us who know the codebase well enough can
readily tell that this tree is actually a rewrite. There's no items.c at
all, there're new files spread about, #ifdef's everywhere. Also as Dustin
said the original diffs were longer than the original codebase.

During our last discussion at the hackathon in october, we talked about
our inability to work with the original code dump. I had directly asked
for "at least a tree with history", so we could get a *hint* of insight
into what the changes were, and get smaller diffs to examine. The github
repository is exactly this. I even okay'ed the usage of github instead of
an SVN branch. Easier for all of us to work against.

The hope was that we'd be able to work together on messaging and figuring
out /what parts/ of the tree were mergable. Instead I've been reading a
flood from users chattering about the amazingly performant facebook fork
of memcached. - while it's an implementation of memcached provided by
facebook, I'm hard pressed to consider it a fork at this point. As another
poster has pointed out, FB isn't obligated to do anything, even a code
dump is nice. However, most people don't put up code dumps and claim them
as merge requests.

Even on other projects that I effectively own now (see: MogileFS) I
actually bother to rewrite topic branches into clean mail-able, documented
patchsets, which go up for review. This is a project where I really don't
have to do that at all, and the changes are all internal
performance/feature fixes for livejournal and typepad.

A lot of things stand between us and mergability:

- The FB tree is not compatible with either tree, as CAS was removed.
Counters are also very different, but that's minor. Trond has a patch
making the CAS requirement a runtime option... I haven't examined it yet,
but I recall the FB complaint was not wanting to waste 8 bytes per item
storing the CAS identifier.

- The FB tree contains a binary protocol that was proprietary up until the
release. The memcached binary protocol we have was designed and written by
a consortium of users, and has existing clients.

- The FB tree contains a weird mishmash of storage engines. Flat
allocator? Ok. Memory pools, ok... #ifdef's for the old engine. Fair
enough. The memcached community (mainly Toru and Trond) have been working
towards a pluggable storage engine interface for memcached. With the
intention of pulling in a lot of these forks, and allowing us to ship
multiple storage engines which can be runtime pluggable.

I recall this was brought up during the hackathon, and FB had serious
concerns about the usage of indirect function calls for a storage engine
interface. You'd prefer to #ifdef and compile it all out in order to save
a few cycles from some primary calls. This goes against what the
community has been working towards. (there're even handy public drafts of
the interface: http://code.google.com/p/memcached/wiki/EngineInterface).

- The FB tree contains dead ends, debug code, and dangerous features. We
would never release 'flush_regex' on the main release. Not on purpose,
anyway.

- All of the stats output code was rewritten into long, ugly
'append_to_buffer' lines. This doesn't seem necessary, and fills in the
gap of what little code wasn't rewritten elsewhere...

- The FB tree appears to have written very few, if any, tests around its
changes. Do your tests exist in a different tree, or do they not exist?

- Being nitpicky, the changelog wasn't even updated :)

---

There are certainly interesting things in the branch that we'd like. Maybe
the flat allocator? I don't know. Certainly bugfixes, the stats lock
changes, and the per-thread memory pools.

During the hackathons, in IRC, and elsewhere, we've been discussing
changes around the client memory buffers and the stats locks. I've been
personally nitpicky about the connection buffers. In my MySQL Proxy I'd
prototyped a shared connection buffer, so idle connections would use a
minimal amount of memory. This seemed like a good idea, but hadn't come up
on the 'super important' radar for memcached - the binary protocol seemed
more important, as it increases flexiblity for users. In the grand scheme
of things they need that more than extra speed. That's dangerous for me to
say, I know, but true.

The other thing are the stats locks. It'll be fun to see how you folks did
it, since I couldn't figure out how it was done without memory barriers on
the thread-local level. Or if that just worked okay. The "correct way" is
to use atomic CAS around a many-writer single-reader or single-writer
single-reader pattern. Which suck a bit for 8 byte values, and aren't
perfectly fast since they are still memory barriers.

What else is merge worthy? I'm not sure. The facebook article seems to
mention a lot of linux kernel hacks were required in order to achieve that
speed. How does the FB branch benchmark without those kernel
modifications? Are those changes also public?

If you folks are truly uninterested in maintaining a "fork" of the
software, you'll have to decide what distinct changes actually go
upstream. We have a binary protocol, we have a storage engine interface on
the way, and many of the other changes are unmergable. Will you work with
us to get the most beneficial performance changes upstream and adopt the
main tree, or continue to use your internal tree? We have to decide what
work will be merged at all before flocking to a "merge-a-thon".

have fun,
-Dormando

Reply via email to