diff --git a/osbase/event/memory/BUILD.bazel b/osbase/event/memory/BUILD.bazel
new file mode 100644
index 0000000..f2cd4bd
--- /dev/null
+++ b/osbase/event/memory/BUILD.bazel
@@ -0,0 +1,19 @@
+load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
+
+go_library(
+    name = "memory",
+    srcs = ["memory.go"],
+    importpath = "source.monogon.dev/osbase/event/memory",
+    visibility = ["//visibility:public"],
+    deps = ["//osbase/event"],
+)
+
+go_test(
+    name = "memory_test",
+    srcs = [
+        "example_test.go",
+        "memory_test.go",
+    ],
+    embed = [":memory"],
+    deps = ["//osbase/event"],
+)
diff --git a/osbase/event/memory/example_test.go b/osbase/event/memory/example_test.go
new file mode 100644
index 0000000..1ae12c6
--- /dev/null
+++ b/osbase/event/memory/example_test.go
@@ -0,0 +1,114 @@
+// Copyright 2020 The Monogon Project Authors.
+//
+// SPDX-License-Identifier: Apache-2.0
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//     http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package memory
+
+import (
+	"context"
+	"fmt"
+	"net"
+	"time"
+)
+
+// NetworkStatus is example data that will be stored in a Value.
+type NetworkStatus struct {
+	ExternalAddress net.IP
+	DefaultGateway  net.IP
+}
+
+// NetworkService is a fake/example network service that is responsible for
+// communicating the newest information about a machine's network configuration
+// to consumers/watchers.
+type NetworkService struct {
+	Provider Value[NetworkStatus]
+}
+
+// Run pretends to execute the network service's main logic loop, in which it
+// pretends to have received an IP address over DHCP, and communicates that to
+// consumers/watchers.
+func (s *NetworkService) Run(ctx context.Context) {
+	s.Provider.Set(NetworkStatus{
+		ExternalAddress: nil,
+		DefaultGateway:  nil,
+	})
+
+	select {
+	case <-time.After(100 * time.Millisecond):
+	case <-ctx.Done():
+		return
+	}
+
+	fmt.Printf("NS: Got DHCP Lease\n")
+	s.Provider.Set(NetworkStatus{
+		ExternalAddress: net.ParseIP("203.0.113.24"),
+		DefaultGateway:  net.ParseIP("203.0.113.1"),
+	})
+
+	select {
+	case <-time.After(100 * time.Millisecond):
+	case <-ctx.Done():
+		return
+	}
+
+	fmt.Printf("NS: DHCP Address changed\n")
+	s.Provider.Set(NetworkStatus{
+		ExternalAddress: net.ParseIP("203.0.113.103"),
+		DefaultGateway:  net.ParseIP("203.0.113.1"),
+	})
+
+	time.Sleep(100 * time.Millisecond)
+}
+
+// ExampleValue_full demonstrates a typical usecase for Event Values, in which
+// a mock network service lets watchers know that the machine on which the code
+// is running has received a new network configuration.
+// It also shows the typical boilerplate required in order to wrap a Value (eg.
+// MemoryValue) within a typesafe wrapper.
+func ExampleValue_full() {
+	ctx, ctxC := context.WithCancel(context.Background())
+	defer ctxC()
+
+	// Create a fake NetworkService.
+	var ns NetworkService
+
+	// Run an /etc/hosts updater. It will watch for updates from the NetworkService
+	// about the current IP address of the node.
+	go func() {
+		w := ns.Provider.Watch()
+		for {
+			status, err := w.Get(ctx)
+			if err != nil {
+				break
+			}
+			if status.ExternalAddress == nil {
+				continue
+			}
+			// Pretend to write /etc/hosts with the newest ExternalAddress.
+			// In production code, you would also check for whether ExternalAddress has
+			// changed from the last written value, if writing to /etc/hosts is expensive.
+			fmt.Printf("/etc/hosts: foo.example.com is now %s\n", status.ExternalAddress.String())
+		}
+	}()
+
+	// Run fake network service.
+	ns.Run(ctx)
+
+	// Output:
+	// NS: Got DHCP Lease
+	// /etc/hosts: foo.example.com is now 203.0.113.24
+	// NS: DHCP Address changed
+	// /etc/hosts: foo.example.com is now 203.0.113.103
+}
diff --git a/osbase/event/memory/memory.go b/osbase/event/memory/memory.go
new file mode 100644
index 0000000..16818a0
--- /dev/null
+++ b/osbase/event/memory/memory.go
@@ -0,0 +1,233 @@
+// Copyright 2020 The Monogon Project Authors.
+//
+// SPDX-License-Identifier: Apache-2.0
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//     http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package memory
+
+import (
+	"context"
+	"errors"
+	"fmt"
+	"sync"
+
+	"source.monogon.dev/osbase/event"
+)
+
+var (
+	// Type assert that *Value implements Value. We do this artificially, as
+	// there currently is no code path that needs this to be strictly true. However,
+	// users of this library might want to rely on the Value type instead of
+	// particular Value implementations.
+	_ event.Value[int] = &Value[int]{}
+)
+
+// Value is a 'memory value', which implements a event.Value stored in memory.
+// It is safe to construct an empty object of this type. However, this must not
+// be copied.
+type Value[T any] struct {
+	// mu guards the inner, innerSet and watchers fields.
+	mu sync.RWMutex
+	// inner is the latest data Set on the Value. It is used to provide the
+	// newest version of the Set data to new watchers.
+	inner T
+	// innerSet is true when inner has been Set at least once. It is used to
+	// differentiate between a nil and unset value.
+	innerSet bool
+	// watchers is the list of watchers that should be updated when new data is
+	// Set. It will grow on every .Watch() and shrink any time a watcher is
+	// determined to have been closed.
+	watchers []*watcher[T]
+
+	// Sync, if set to true, blocks all .Set() calls on the Value until all
+	// Watchers derived from it actively .Get() the new value. This can be used
+	// to ensure Watchers always receive a full log of all Set() calls.
+	//
+	// This must not be changed after the first .Set/.Watch call.
+	//
+	// This is an experimental API and subject to change. It might be migrated
+	// to per-Watcher settings defined within the main event.Value/Watcher
+	// interfaces.
+	Sync bool
+}
+
+// Set updates the Value to the given data. It is safe to call this from
+// multiple goroutines, including concurrently.
+//
+// For more information about guarantees, see event.Value.Set.
+func (m *Value[T]) Set(val T) {
+	m.mu.Lock()
+	defer m.mu.Unlock()
+
+	// Update the data that is provided on first Get() to watchers.
+	m.inner = val
+	m.innerSet = true
+
+	// Go through all watchers, updating them on the new value and filtering out
+	// all closed watchers.
+	newWatchers := m.watchers[:0]
+	for _, w := range m.watchers {
+		if w.closed() {
+			continue
+		}
+		w.update(m.Sync, val)
+		newWatchers = append(newWatchers, w)
+	}
+	if cap(newWatchers) > len(newWatchers)*3 {
+		reallocated := make([]*watcher[T], 0, len(newWatchers)*2)
+		newWatchers = append(reallocated, newWatchers...)
+	}
+	m.watchers = newWatchers
+}
+
+// watcher implements the event.Watcher interface for watchers returned by
+// Value.
+type watcher[T any] struct {
+	// bufferedC is a buffered channel of size 1 for submitting values to the
+	// watcher.
+	bufferedC chan T
+	// unbufferedC is an unbuffered channel, which is used when Sync is enabled.
+	unbufferedC chan T
+
+	// getSem is a channel-based semaphore (which is of size 1, and thus in
+	// fact a mutex) that is used to ensure that only a single .Get() call is
+	// active. It is implemented as a channel to permit concurrent .Get() calls
+	// to error out instead of blocking.
+	getSem chan struct{}
+	// close is a channel that is closed when this watcher is itself Closed.
+	close chan struct{}
+}
+
+// Watch retrieves a Watcher that keeps track on the version of the data
+// contained within the Value that was last seen by a consumer.
+//
+// For more information about guarantees, see event.Value.Watch.
+func (m *Value[T]) Watch() event.Watcher[T] {
+	waiter := &watcher[T]{
+		bufferedC:   make(chan T, 1),
+		unbufferedC: make(chan T),
+		close:       make(chan struct{}),
+		getSem:      make(chan struct{}, 1),
+	}
+
+	m.mu.Lock()
+	// If the watchers slice is at capacity, drop closed watchers, and
+	// reallocate the slice at 2x length if it is not between 1.5x and 3x.
+	if len(m.watchers) == cap(m.watchers) {
+		newWatchers := m.watchers[:0]
+		for _, w := range m.watchers {
+			if !w.closed() {
+				newWatchers = append(newWatchers, w)
+			}
+		}
+		if cap(newWatchers)*2 < len(newWatchers)*3 || cap(newWatchers) > len(newWatchers)*3 {
+			reallocated := make([]*watcher[T], 0, len(newWatchers)*2)
+			newWatchers = append(reallocated, newWatchers...)
+		}
+		m.watchers = newWatchers
+	}
+	// Append this watcher to the Value.
+	m.watchers = append(m.watchers, waiter)
+	// If the Value already has some value set, put it in the buffered channel.
+	if m.innerSet {
+		waiter.bufferedC <- m.inner
+	}
+	m.mu.Unlock()
+
+	return waiter
+}
+
+// closed returns whether this watcher has been closed.
+func (m *watcher[T]) closed() bool {
+	select {
+	case _, ok := <-m.close:
+		if !ok {
+			return true
+		}
+	default:
+	}
+	return false
+}
+
+// update is the high level update-this-watcher function called by Value.
+func (m *watcher[T]) update(sync bool, val T) {
+	// If synchronous delivery was requested, block until a watcher .Gets it,
+	// or is closed.
+	if sync {
+		select {
+		case m.unbufferedC <- val:
+		case <-m.close:
+		}
+		return
+	}
+
+	// Otherwise, deliver asynchronously. If there is already a value in the
+	// buffered channel that was not retrieved, drop it.
+	select {
+	case <-m.bufferedC:
+	default:
+	}
+	// The channel is now empty, so sending to it cannot block.
+	m.bufferedC <- val
+}
+
+func (m *watcher[T]) Close() error {
+	close(m.close)
+	return nil
+}
+
+// Get blocks until a Value's data is available. See event.Watcher.Get for
+// guarantees and more information.
+func (m *watcher[T]) Get(ctx context.Context, opts ...event.GetOption[T]) (T, error) {
+	// Make sure we're the only active .Get call.
+	var empty T
+	select {
+	case m.getSem <- struct{}{}:
+	default:
+		return empty, fmt.Errorf("cannot Get() concurrently on a single waiter")
+	}
+	defer func() {
+		<-m.getSem
+	}()
+
+	var predicate func(t T) bool
+	for _, opt := range opts {
+		if opt.Predicate != nil {
+			predicate = opt.Predicate
+		}
+		if opt.BacklogOnly {
+			return empty, errors.New("BacklogOnly is not implemented for memory watchers")
+		}
+	}
+
+	for {
+		var val T
+		// For Sync values, ensure the initial value in the buffered
+		// channel is delivered first.
+		select {
+		case val = <-m.bufferedC:
+		default:
+			select {
+			case <-ctx.Done():
+				return empty, ctx.Err()
+			case val = <-m.bufferedC:
+			case val = <-m.unbufferedC:
+			}
+		}
+		if predicate != nil && !predicate(val) {
+			continue
+		}
+		return val, nil
+	}
+}
diff --git a/osbase/event/memory/memory_test.go b/osbase/event/memory/memory_test.go
new file mode 100644
index 0000000..b622565
--- /dev/null
+++ b/osbase/event/memory/memory_test.go
@@ -0,0 +1,371 @@
+// Copyright 2020 The Monogon Project Authors.
+//
+// SPDX-License-Identifier: Apache-2.0
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//     http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package memory
+
+import (
+	"context"
+	"errors"
+	"fmt"
+	"sync"
+	"sync/atomic"
+	"testing"
+	"time"
+
+	"source.monogon.dev/osbase/event"
+)
+
+// TestAsync exercises the high-level behaviour of a Value, in which a
+// watcher is able to catch up to the newest Set value.
+func TestAsync(t *testing.T) {
+	p := Value[int]{}
+	p.Set(0)
+
+	ctx := context.Background()
+
+	// The 0 from Set() should be available via .Get().
+	watcher := p.Watch()
+	val, err := watcher.Get(ctx)
+	if err != nil {
+		t.Fatalf("Get: %v", err)
+	}
+	if want, got := 0, val; want != got {
+		t.Fatalf("Value: got %d, wanted %d", got, want)
+	}
+
+	// Send a large amount of updates that the watcher does not actively .Get().
+	for i := 1; i <= 100; i++ {
+		p.Set(i)
+	}
+
+	// The watcher should still end up with the newest .Set() value on the next
+	// .Get() call.
+	val, err = watcher.Get(ctx)
+	if err != nil {
+		t.Fatalf("Get: %v", err)
+	}
+	if want, got := 100, val; want != got {
+		t.Fatalf("Value: got %d, wanted %d", got, want)
+	}
+}
+
+// TestSyncBlocks exercises the Value's 'Sync' field, which makes all
+// Set() calls block until all respective watchers .Get() the updated data.
+// This particular test ensures that .Set() calls to a Watcher result in a
+// prefect log of updates being transmitted to a watcher.
+func TestSync(t *testing.T) {
+	p := Value[int]{
+		Sync: true,
+	}
+	values := make(chan int, 100)
+	var wg sync.WaitGroup
+	wg.Add(1)
+	go func() {
+		ctx := context.Background()
+		watcher := p.Watch()
+		wg.Done()
+		for {
+			value, err := watcher.Get(ctx)
+			if err != nil {
+				panic(err)
+			}
+			values <- value
+		}
+	}()
+
+	p.Set(0)
+	wg.Wait()
+
+	want := []int{1, 2, 3, 4}
+	for _, w := range want {
+		p.Set(w)
+	}
+
+	timeout := time.After(time.Second)
+	for i, w := range append([]int{0}, want...) {
+		select {
+		case <-timeout:
+			t.Fatalf("timed out on value %d (%d)", i, w)
+		case val := <-values:
+			if w != val {
+				t.Errorf("value %d was %d, wanted %d", i, val, w)
+			}
+		}
+	}
+}
+
+// TestSyncBlocks exercises the Value's 'Sync' field, which makes all
+// Set() calls block until all respective watchers .Get() the updated data.
+// This particular test ensures that .Set() calls actually block when a watcher
+// is unattended.
+func TestSyncBlocks(t *testing.T) {
+	p := Value[int]{
+		Sync: true,
+	}
+	ctx := context.Background()
+
+	// Shouldn't block, as there's no declared watchers.
+	p.Set(0)
+
+	watcher := p.Watch()
+
+	// Should retrieve the zero, more requests will pend.
+	value, err := watcher.Get(ctx)
+	if err != nil {
+		t.Fatalf("Get: %v", err)
+	}
+	if want, got := 0, value; want != got {
+		t.Fatalf("Got initial value %d, wanted %d", got, want)
+	}
+
+	// .Set() Should block, as watcher is unattended.
+	//
+	// Whether something blocks in Go is untestable in a robust way (see: halting
+	// problem). We work around this this by introducing a 'stage' int64, which is
+	// put on the 'c' channel after the needs-to-block function returns. We then
+	// perform an action that should unblock this function right after updating
+	// 'stage' to a different value.
+	// Then, we observe what was put on the channel: If it's the initial value, it
+	// means the function didn't block when expected. Otherwise, it means the
+	// function unblocked when expected.
+	stage := int64(0)
+	c := make(chan int64, 1)
+	go func() {
+		p.Set(1)
+		c <- atomic.LoadInt64(&stage)
+	}()
+
+	// Getting should unblock the provider. Mark via 'stage' variable that
+	// unblocking now is expected.
+	atomic.StoreInt64(&stage, int64(1))
+	// Potential race: .Set() unblocks here due to some bug, before .Get() is
+	// called, and we record a false positive.
+	value, err = watcher.Get(ctx)
+	if err != nil {
+		t.Fatalf("Get: %v", err)
+	}
+
+	res := <-c
+	if res != int64(1) {
+		t.Fatalf("Set() returned before Get()")
+	}
+
+	if want, got := 1, value; want != got {
+		t.Fatalf("Wanted value %d, got %d", want, got)
+	}
+
+	// Closing the watcher and setting should not block anymore.
+	if err := watcher.Close(); err != nil {
+		t.Fatalf("Close: %v", err)
+	}
+	// Last step, if this blocks we will get a deadlock error and the test will panic.
+	p.Set(2)
+}
+
+// TestMultipleGets verifies that calling .Get() on a single watcher from two
+// goroutines is prevented by returning an error in exactly one of them.
+func TestMultipleGets(t *testing.T) {
+	p := Value[int]{}
+	ctx := context.Background()
+
+	w := p.Watch()
+
+	tryError := func(errs chan error) {
+		_, err := w.Get(ctx)
+		errs <- err
+	}
+	errs := make(chan error, 2)
+	go tryError(errs)
+	go tryError(errs)
+
+	for err := range errs {
+		if err == nil {
+			t.Fatalf("A Get call succeeded, while it should have blocked or returned an error")
+		} else {
+			// Found the error, test succeeded.
+			break
+		}
+	}
+}
+
+// TestConcurrency attempts to stress the Value/Watcher
+// implementation to design limits (a hundred simultaneous watchers), ensuring
+// that the watchers all settle to the final set value.
+func TestConcurrency(t *testing.T) {
+	ctx := context.Background()
+
+	p := Value[int]{}
+	p.Set(0)
+
+	// Number of watchers to create.
+	watcherN := 100
+	// Expected final value to be Set().
+	final := 100
+	// Result channel per watcher.
+	resC := make([]chan error, watcherN)
+
+	// Spawn watcherN watchers.
+	for i := 0; i < watcherN; i++ {
+		resC[i] = make(chan error, 1)
+		go func(id int) {
+			// done is a helper function that will put an error on the
+			// respective watcher's resC.
+			done := func(err error) {
+				resC[id] <- err
+				close(resC[id])
+			}
+
+			watcher := p.Watch()
+			// prev is used to ensure the values received are monotonic.
+			prev := -1
+			for {
+				val, err := watcher.Get(ctx)
+				if err != nil {
+					done(err)
+					return
+				}
+
+				// Ensure monotonicity of received data.
+				if val <= prev {
+					done(fmt.Errorf("received out of order data: %d after %d", val, prev))
+				}
+				prev = val
+
+				// Quit when the final value is received.
+				if val == final {
+					done(nil)
+					return
+				}
+
+				// Sleep a bit, depending on the watcher. This makes each
+				// watcher behave slightly differently, and attempts to
+				// exercise races dependent on sleep time between subsequent
+				// Get calls.
+				time.Sleep(time.Millisecond * time.Duration(id))
+			}
+		}(i)
+	}
+
+	// Set 1..final on the value.
+	for i := 1; i <= final; i++ {
+		p.Set(i)
+	}
+
+	// Ensure all watchers exit with no error.
+	for i, c := range resC {
+		err := <-c
+		if err != nil {
+			t.Errorf("Watcher %d returned %v", i, err)
+		}
+	}
+}
+
+// TestCanceling exercises whether a context canceling in a .Get() gracefully
+// aborts that particular Get call, but also allows subsequent use of the same
+// watcher.
+func TestCanceling(t *testing.T) {
+	p := Value[int]{
+		Sync: true,
+	}
+
+	ctx, ctxC := context.WithCancel(context.Background())
+
+	watcher := p.Watch()
+
+	// errs will contain the error returned by Get.
+	errs := make(chan error, 1)
+	go func() {
+		// This Get will block, as no initial data has been Set on the value.
+		_, err := watcher.Get(ctx)
+		errs <- err
+	}()
+
+	// Cancel the context, and expect that context error to propagate to the .Get().
+	ctxC()
+	if want, got := ctx.Err(), <-errs; !errors.Is(got, want) {
+		t.Fatalf("Get should've returned %v, got %v", want, got)
+	}
+
+	// Do another .Get() on the same watcher with a new context. Even though the
+	// call was aborted via a context cancel, the watcher should continue working.
+	ctx = context.Background()
+	go func() {
+		_, err := watcher.Get(ctx)
+		errs <- err
+	}()
+
+	// Unblock the .Get now.
+	p.Set(1)
+	if want, got := error(nil), <-errs; !errors.Is(got, want) {
+		t.Fatalf("Get should've returned %v, got %v", want, got)
+	}
+}
+
+// TestSetAfterWatch ensures that if a value is updated between a Watch and the
+// initial Get, only the newest Set value is returns.
+func TestSetAfterWatch(t *testing.T) {
+	ctx := context.Background()
+
+	p := Value[int]{}
+	p.Set(0)
+
+	watcher := p.Watch()
+	p.Set(1)
+
+	data, err := watcher.Get(ctx)
+	if err != nil {
+		t.Fatalf("Get: %v", err)
+	}
+	if want, got := 1, data; want != got {
+		t.Errorf("Get should've returned %v, got %v", want, got)
+	}
+}
+
+// TestWatchersList ensures that the list of watchers is managed correctly,
+// i.e. there is no memory leak and closed watchers are removed while
+// keeping all non-closed watchers.
+func TestWatchersList(t *testing.T) {
+	ctx := context.Background()
+	p := Value[int]{}
+
+	var watchers []event.Watcher[int]
+	for i := 0; i < 100; i++ {
+		watchers = append(watchers, p.Watch())
+	}
+	for i := 0; i < 10000; i++ {
+		watchers[10].Close()
+		watchers[10] = p.Watch()
+	}
+
+	if want, got := 1000, cap(p.watchers); want <= got {
+		t.Fatalf("Got capacity %d, wanted less than %d", got, want)
+	}
+
+	p.Set(1)
+	if want, got := 100, len(p.watchers); want != got {
+		t.Fatalf("Got %d watchers, wanted %d", got, want)
+	}
+
+	for _, watcher := range watchers {
+		data, err := watcher.Get(ctx)
+		if err != nil {
+			t.Fatalf("Get: %v", err)
+		}
+		if want, got := 1, data; want != got {
+			t.Errorf("Get should've returned %v, got %v", want, got)
+		}
+	}
+}
