diff --git a/ChangeLog.md b/ChangeLog.md
--- a/ChangeLog.md
+++ b/ChangeLog.md
@@ -1,5 +1,12 @@
 # dnf-repo releases
 
+## 0.4 (2022-10-20)
+- only list all repos if --list or no repo actions
+- repo patterns can now use a ^ prefix and $ suffix
+- add --disable/enable-defaults for Fedora modular and cisco h264 repos
+- add --(no-)weak-deps options (-W/-w)
+- transform / to : in any given repo pattern
+
 ## 0.3 (2022-08-12)
 - fold over multiple changes (eg -m -t now combine correctly)
 - handle debuginfo and source repos
diff --git a/README.md b/README.md
--- a/README.md
+++ b/README.md
@@ -1,10 +1,12 @@
 # dnf-repo
 
-A wrapper of the  dnf package manager for fine control of enabled/disabled yum repos (eg coprs).
+A wrapper of the dnf package manager for fine control of
+enabled/disabled yum repos (eg coprs).
 
 DNF is not terribly fast at handling repos partly because it likes
 to refresh the cached repodata frequently. So it can be advantageous
-to disable smaller repos by default and only enable them as needed.
+to disable smaller repos by default and only enable them as needed
+(eg periodically).
 
 This tool can temporarily enable/disable repos selected by substring.
 Repo states can also be saved or their cache individually expired.
@@ -16,18 +18,21 @@
 
 ```shellsession
 $ dnf-repo --version
-0.3
+0.4
 $ dnf-repo --help
 DNF wrapper repo tool
 
-Usage: dnf-repo [--version] [-n|--dryrun] [-D|--debug] [--exact] [-s|--save]
-                [(-c|--add-copr COPR) | (-k|--add-koji REPO) |
-                  (-d|--disable REPOPAT) | (-e|--enable REPOPAT) |
-                  (-x|--expire REPOPAT) | (-E|--delete-repofile REPOPAT) |
-                  (-t|--enable-testing) | (-T|--disable-testing) |
-                  (-m|--enable-modular) | (-M|--disable-modular) |
-                  --enable-debuginfo | --disable-debuginfo | --enable-source |
-                  --disable-source] [DNFARGS]
+Usage: dnf-repo [--version] [-n|--dryrun] [-D|--debug] [-l|--list] [--exact]
+                [-s|--save] [(-w|--weak-deps) | (-W|--no-weak-deps)]
+                [
+                  [(-c|--add-copr COPR) | (-k|--add-koji REPO) |
+                    (-d|--disable REPOPAT) | (-e|--enable REPOPAT) |
+                    (-x|--expire REPOPAT) | (-E|--delete-repofile REPOPAT) |
+                    (-t|--enable-testing) | (-T|--disable-testing) |
+                    (-m|--enable-modular) | (-M|--disable-modular) |
+                    --enable-debuginfo | --disable-debuginfo | --enable-source |
+                    --disable-source] |
+                  --enable-defaults | --disable-defaults] [DNFARGS]
   see https://github.com/juhp/dnf-repo#readme
 
 Available options:
@@ -35,8 +40,11 @@
   --version                Show version
   -n,--dryrun              Dry run
   -D,--debug               Debug output
+  -l,--list                List all repos
   --exact                  Match repo names exactly
   -s,--save                Save the repo enable/disable state
+  -w,--weak-deps           Use weak dependencies
+  -W,--no-weak-deps        Disable weak dependencies
   -c,--add-copr COPR       Create repo file for copr repo
   -k,--add-koji REPO       Create repo file for koji repo
   -d,--disable REPOPAT     Disable repos
@@ -52,6 +60,8 @@
   --disable-debuginfo      Disable debuginfo repos
   --enable-source          Enable source repos
   --disable-source         Disable source repos
+  --enable-defaults        Enable modular and Cisco h264 repos
+  --disable-defaults       Disable modular and Cisco h264 repos
 ```
 
 ## Usage examples
@@ -65,6 +75,10 @@
 $ dnf-repo -t update
 ```
 
+Note that sudo is used implicitly when needed:
+there is no need to run dnf-repo with sudo.
+
+### Copr
 List disabled copr repos (actually shows "copr" repos that would be enabled):
 ```shellsession
 $ dnf-repo -e copr
@@ -75,25 +89,41 @@
 $ dnf-repo -d copr update
 ```
 
-Disable modular repos permanently:
+Install a package directly from a new copr:
 ```shellsession
-$ dnf-repo --disable-modular --save
+$ dnf-repo -c varlad/helix install helix
 ```
-(or equivalently `dnf-repo -M -s`).
+(note the copr repo is not permanently enabled by default).
 
+Later update with the copr:
+```shellsession
+$ dnf-repo -e helix update
+```
+
+### Changing system repo config
+Disable modular and cisco h264 repos permanently:
+```shellsession
+$ dnf-repo --disable-defaults --save
+```
+
+To only disable modular you can use: `dnf-repo -M -s`.
+
+### Switch system from rawhide
 Switch a system from Rawhide to F37:
 ```shellsession
 $ dnf-repo --exact -d rawhide -e fedora distrosync --releasever 37 fedora\*
 ```
 
-Note that sudo is used implicitly when needed:
-there is no need to run dnf-repo with sudo.
+### Repo patterns
+By default repo patterns are matched as infix substrings
+(unless you use `--exact`).
 
-## Installation
+But you can also prepend `^`/append `$` (or both) to match a repo name
+from its beginning/end (or exactly).
 
+## Installation
 A copr repo is available:
 <https://copr.fedorainfracloud.org/coprs/petersen/dnf-repo/>
 
 ## Building
-
 Use {cabal,stack,cabal-rpm} install.
diff --git a/dnf-repo.cabal b/dnf-repo.cabal
--- a/dnf-repo.cabal
+++ b/dnf-repo.cabal
@@ -1,5 +1,5 @@
 name:                dnf-repo
-version:             0.3
+version:             0.4
 synopsis:            DNF wrapper tool to control repos
 description:
         A command-line wrapper of the dnf package manager to
diff --git a/src/Main.hs b/src/Main.hs
--- a/src/Main.hs
+++ b/src/Main.hs
@@ -29,18 +29,31 @@
     runMain
     <$> switchWith 'n' "dryrun" "Dry run"
     <*> switchWith 'D' "debug" "Debug output"
+    <*> switchWith 'l' "list" "List all repos"
     <*> switchLongWith "exact" "Match repo names exactly"
     <*> switchWith 's' "save" "Save the repo enable/disable state"
-    <*> many modeOpt
+    <*> optional (flagWith' True 'w' "weak-deps" "Use weak dependencies" <|>
+                  flagWith' False 'W' "no-weak-deps" "Disable weak dependencies")
+    <*> (many modeOpt <|>
+         (flagLongWith' [Specific EnableModular,
+                         EnableRepo "^fedora-cisco-openh264$"]
+          "enable-defaults" "Enable modular and Cisco h264 repos"
+          <|>
+          flagLongWith [] [Specific DisableModular,
+                           DisableRepo "^fedora-cisco-openh264$"]
+          "disable-defaults" "Disable modular and Cisco h264 repos"))
     <*> many (strArg "DNFARGS")
   where
+    repoOptionWith =
+      (fmap . fmap . fmap . fmap) (replace "/" ":") . strOptionWith
+
     modeOpt =
-      AddCopr . replace "/" ":" <$> strOptionWith 'c' "add-copr" "COPR" "Create repo file for copr repo" <|>
-      AddKoji <$> strOptionWith 'k' "add-koji" "REPO" "Create repo file for koji repo" <|>
-      DisableRepo <$> strOptionWith 'd' "disable" "REPOPAT" "Disable repos" <|>
-      EnableRepo <$> strOptionWith 'e' "enable" "REPOPAT" "Enable repos" <|>
-      ExpireRepo <$> strOptionWith 'x' "expire" "REPOPAT" "Expire repo cache" <|>
-      DeleteRepo <$> strOptionWith 'E' "delete-repofile" "REPOPAT" "Remove unwanted .repo file" <|>
+      AddCopr <$> repoOptionWith 'c' "add-copr" "COPR" "Create repo file for copr repo" <|>
+      AddKoji <$> repoOptionWith 'k' "add-koji" "REPO" "Create repo file for koji repo" <|>
+      DisableRepo <$> repoOptionWith 'd' "disable" "REPOPAT" "Disable repos" <|>
+      EnableRepo <$> repoOptionWith 'e' "enable" "REPOPAT" "Enable repos" <|>
+      ExpireRepo <$> repoOptionWith 'x' "expire" "REPOPAT" "Expire repo cache" <|>
+      DeleteRepo <$> repoOptionWith 'E' "delete-repofile" "REPOPAT" "Remove unwanted .repo file" <|>
       flagWith' (Specific EnableTesting) 't' "enable-testing" "Enable testing repos" <|>
       flagWith' (Specific DisableTesting) 'T' "disable-testing" "Disable testing repos" <|>
       flagWith' (Specific EnableModular) 'm' "enable-modular" "Enable modular repos" <|>
@@ -60,8 +73,9 @@
 -- FIXME --enable-all-coprs (for updating etc)
 -- FIXME confirm repos if many
 -- FIXME --disable-non-cores (modular,testing,cisco, etc)
-runMain :: Bool -> Bool -> Bool -> Bool -> [Mode] -> [String] -> IO ()
-runMain dryrun debug exact save modes args = do
+runMain :: Bool -> Bool -> Bool -> Bool -> Bool -> Maybe Bool -> [Mode]
+        -> [String] -> IO ()
+runMain dryrun debug listrepos exact save mweakdeps modes args = do
   hSetBuffering stdout NoBuffering
   withCurrentDirectory "/etc/yum.repos.d" $ do
     forM_ modes $
@@ -70,7 +84,7 @@
         AddKoji repo -> addKojiRepo repo
         _ -> return ()
     repofiles <- filesWithExtension "." "repo"
---    when debug $ print repofiles
+    -- when debug $ print repofiles
     nameStates <- sort <$> concatMapM readRepos repofiles
     let repoActs = selectRepo exact nameStates modes
     unless (null repoActs) $ do
@@ -93,13 +107,15 @@
           "config-manager" :
           concatMap saveRepo repoActs
     if null args
-      then do
+      then
+      when (null repoActs || listrepos) $
       listRepos $ map (updateState repoActs) nameStates
       else do
       sleep 1
       putStrLn ""
       let repoargs = concatMap changeRepo repoActs
-        in doSudo dryrun debug "dnf" $ repoargs ++ args
+          weakdeps = maybe [] (\w -> ["--setopt=install_weak_deps=" ++ show w]) mweakdeps
+        in doSudo dryrun debug "dnf" $ repoargs ++ weakdeps ++ args
     where
       -- FIXME pull non-fedora copr repo file
       -- FIXME delete created copr repo file if repo doesn't exist
diff --git a/src/YumRepoFile.hs b/src/YumRepoFile.hs
--- a/src/YumRepoFile.hs
+++ b/src/YumRepoFile.hs
@@ -113,7 +113,17 @@
           enabled == state || Enable repo `elem` acc
         Nothing -> False
 
-    matchesRepo = if exact then (==) else isInfixOf
+    matchesRepo :: String -> String -> Bool
+    matchesRepo "" = error' "empty repo pattern"
+    matchesRepo pat =
+      if exact
+      then (pat ==)
+      else
+        case ('^' == head pat,'$' == last pat) of
+          (True,True) -> (init (tail pat) ==)
+          (True,False) -> (tail pat `isPrefixOf`)
+          (False,True) -> (init pat `isSuffixOf`)
+          _ -> (pat `isInfixOf`)
 
 readRepos :: FilePath -> IO [RepoState]
 readRepos file =
